mirror of
https://github.com/MariaDB/server.git
synced 2025-01-16 12:02:42 +01:00
Merge branch '10.2' of github.com:MariaDB/server into bb-10.2-mariarocks-merge
This commit is contained in:
commit
6b0588018a
2312 changed files with 188819 additions and 61333 deletions
11
.gitignore
vendored
11
.gitignore
vendored
|
@ -49,6 +49,8 @@ extra/comp_err
|
|||
extra/innochecksum
|
||||
extra/jemalloc/build/
|
||||
extra/jemalloc/tmp/
|
||||
extra/mariabackup/mariabackup
|
||||
extra/mariabackup/mbstream
|
||||
extra/my_print_defaults
|
||||
extra/mysql_waitpid
|
||||
extra/mysqld_safe_helper
|
||||
|
@ -124,10 +126,13 @@ scripts/mytop
|
|||
scripts/wsrep_sst_common
|
||||
scripts/wsrep_sst_mysqldump
|
||||
scripts/wsrep_sst_rsync
|
||||
scripts/wsrep_sst_mariabackup
|
||||
scripts/wsrep_sst_xtrabackup
|
||||
scripts/wsrep_sst_xtrabackup-v2
|
||||
scripts/maria_add_gis_sp.sql
|
||||
scripts/maria_add_gis_sp_bootstrap.sql
|
||||
scripts/galera_new_cluster
|
||||
scripts/galera_recovery
|
||||
sql-bench/bench-count-distinct
|
||||
sql-bench/bench-init.pl
|
||||
sql-bench/compare-results
|
||||
|
@ -219,6 +224,7 @@ support-files/config.medium.ini
|
|||
support-files/config.small.ini
|
||||
support-files/mariadb.pc
|
||||
support-files/mariadb@.service
|
||||
support-files/mariadb.service
|
||||
support-files/my-huge.cnf
|
||||
support-files/my-innodb-heavy-4G.cnf
|
||||
support-files/my-large.cnf
|
||||
|
@ -232,6 +238,7 @@ support-files/mysqld_multi.server
|
|||
support-files/wsrep.cnf
|
||||
support-files/wsrep_notify
|
||||
support-files/policy/selinux/mysqld-safe.pp
|
||||
support-files/mariadb.pp
|
||||
tags
|
||||
tests/async_queries
|
||||
tests/bug25714
|
||||
|
@ -248,6 +255,10 @@ storage/mroonga/vendor/groonga/src/groonga-benchmark
|
|||
storage/mroonga/vendor/groonga/src/suggest/groonga-suggest-create-dataset
|
||||
storage/mroonga/mysql-test/mroonga/storage/r/information_schema_plugins.result
|
||||
storage/mroonga/mysql-test/mroonga/storage/r/variable_version.result
|
||||
xxx/*
|
||||
yyy/*
|
||||
zzz/*
|
||||
|
||||
# C and C++
|
||||
|
||||
# Compiled Object files
|
||||
|
|
|
@ -8,8 +8,8 @@ if [[ "${TRAVIS_OS_NAME}" == 'linux' ]]; then
|
|||
CMAKE_OPT="${CMAKE_OPT} -DCMAKE_C_COMPILER_LAUNCHER=ccache -DCMAKE_CXX_COMPILER_LAUNCHER=ccache"
|
||||
fi
|
||||
case ${GCC_VERSION} in
|
||||
5) CXX=clang++-3.9 ;;
|
||||
6) CXX=clang++-4.0 ;;
|
||||
5) CXX=clang++-4.0 ;;
|
||||
6) CXX=clang++-5.0 ;;
|
||||
esac
|
||||
export CXX CC=${CXX/++/}
|
||||
elif [[ "${CXX}" == 'g++' ]]; then
|
||||
|
@ -39,8 +39,4 @@ else
|
|||
fi
|
||||
fi
|
||||
|
||||
# main.mysqlhotcopy_myisam consitently failed in travis containers
|
||||
# https://travis-ci.org/grooverdan/mariadb-server/builds/217661580
|
||||
echo 'main.mysqlhotcopy_myisam : unstable in containers' >> ${TRAVIS_BUILD_DIR}/mysql-test/unstable-tests
|
||||
echo 'archive.mysqlhotcopy_archive : unstable in containers' >> ${TRAVIS_BUILD_DIR}/mysql-test/unstable-tests
|
||||
set +v +x
|
||||
|
|
71
.travis.yml
71
.travis.yml
|
@ -40,15 +40,66 @@ matrix:
|
|||
include:
|
||||
- os: linux
|
||||
compiler: gcc
|
||||
addons:
|
||||
apt:
|
||||
packages: # make sure these match debian/control contents
|
||||
- bison
|
||||
- chrpath
|
||||
- cmake
|
||||
- debhelper
|
||||
- dh-apparmor
|
||||
- dpatch
|
||||
- gdb
|
||||
- libaio-dev
|
||||
- libboost-dev
|
||||
- libcurl3-dev
|
||||
- libdbd-mysql
|
||||
- libjudy-dev
|
||||
- libncurses5-dev
|
||||
- libpam0g-dev
|
||||
- libpcre3-dev
|
||||
- libreadline-gplv2-dev
|
||||
- libstemmer-dev
|
||||
- libssl-dev
|
||||
- libnuma-dev
|
||||
- libxml2-dev
|
||||
- lsb-release
|
||||
- perl
|
||||
- po-debconf
|
||||
- psmisc
|
||||
- zlib1g-dev
|
||||
- libcrack2-dev
|
||||
- cracklib-runtime
|
||||
- libjemalloc-dev
|
||||
- libsnappy-dev
|
||||
- liblzma-dev
|
||||
- libzmq-dev
|
||||
- libdistro-info-perl
|
||||
- uuid-dev
|
||||
- devscripts
|
||||
- fakeroot
|
||||
script:
|
||||
- ${CC} --version ; ${CXX} --version
|
||||
# Just for disabling hotcopy tests for now
|
||||
- source .travis.compiler.sh
|
||||
# https://github.com/travis-ci/travis-ci/issues/7062 - /run/shm isn't writable or executable
|
||||
# in trusty containers
|
||||
- export MTR_MEM=/tmp
|
||||
- env DEB_BUILD_OPTIONS="parallel=6" debian/autobake-deb.sh;
|
||||
- ccache --show-stats
|
||||
# Until OSX becomes a bit more stable: MDEV-12435
|
||||
allow_failures:
|
||||
- os: osx
|
||||
compiler: clang
|
||||
env: GCC_VERSION=4.8 TYPE=RelWithDebInfo MYSQL_TEST_SUITES=rpl
|
||||
- os: osx
|
||||
compiler: clang
|
||||
env: GCC_VERSION=5 TYPE=RelWithDebInfo MYSQL_TEST_SUITES=main,archive,optimizer_unfixed_bugs,parts,sys_vars,unit,vcol,innodb,innodb_gis,innodb_zip,innodb_fts
|
||||
- os: osx
|
||||
compiler: clang
|
||||
env: GCC_VERSION=6 TYPE=RelWithDebInfo MYSQL_TEST_SUITES=binlog,binlog_encryption,encryption,rocksdb
|
||||
- os: osx
|
||||
compiler: clang
|
||||
env: GCC_VERSION=6 TYPE=RelWithDebInfo MYSQL_TEST_SUITES=csv,federated,funcs_1,funcs_2,gcol,handler,heap,json,maria,percona,perfschema,plugins,multi_source,roles
|
||||
|
||||
# Matrix include for coverity
|
||||
# - env:
|
||||
|
@ -85,29 +136,26 @@ addons:
|
|||
apt:
|
||||
sources:
|
||||
- ubuntu-toolchain-r-test
|
||||
- llvm-toolchain-trusty
|
||||
- llvm-toolchain-trusty-3.9
|
||||
- llvm-toolchain-trusty-4.0
|
||||
packages: # make sure these match debian/control contents
|
||||
- sourceline: 'deb http://apt.llvm.org/trusty/ llvm-toolchain-trusty-5.0 main'
|
||||
packages: # make sure these match the build requirements
|
||||
- gcc-5
|
||||
- g++-5
|
||||
- gcc-6
|
||||
- g++-6
|
||||
- clang-3.9
|
||||
- llvm-3.9-dev
|
||||
- clang-4.0
|
||||
- llvm-4.0-dev
|
||||
- clang-5.0
|
||||
- llvm-5.0-dev
|
||||
- libasan0
|
||||
- bison
|
||||
- chrpath
|
||||
- cmake
|
||||
- debhelper
|
||||
- dh-apparmor
|
||||
- dpatch
|
||||
- gdb
|
||||
- libaio-dev
|
||||
- libboost-dev
|
||||
- libcurl3-dev
|
||||
- libdbd-mysql
|
||||
- libjudy-dev
|
||||
- libncurses5-dev
|
||||
- libpam0g-dev
|
||||
|
@ -119,16 +167,15 @@ addons:
|
|||
- libxml2-dev
|
||||
- lsb-release
|
||||
- perl
|
||||
- po-debconf
|
||||
- psmisc
|
||||
- zlib1g-dev
|
||||
- libcrack2-dev
|
||||
- cracklib-runtime
|
||||
- libjemalloc-dev
|
||||
- libsnappy-dev
|
||||
- liblzma-dev
|
||||
- libzmq-dev
|
||||
- libdistro-info-perl
|
||||
- devscripts # implicit for any build on Ubuntu
|
||||
- uuid-dev
|
||||
|
||||
# libsystemd-daemon-dev # https://github.com/travis-ci/apt-package-whitelist/issues/3882
|
||||
|
||||
|
|
|
@ -35,6 +35,11 @@ fi
|
|||
# git clean -fdX removes all ignored (build) files
|
||||
commands="\
|
||||
git clean -fdX
|
||||
cd ./libmariadb
|
||||
git submodule update
|
||||
cd ../storage/rocksdb/rocksdb
|
||||
git submodule update
|
||||
cd ../../..
|
||||
|
||||
path=`dirname $0`
|
||||
. \"$path/autorun.sh\""
|
||||
|
|
|
@ -205,7 +205,7 @@ fi
|
|||
|
||||
max_no_embedded_configs="$SSL_LIBRARY --with-plugins=max"
|
||||
max_no_qc_configs="$SSL_LIBRARY --with-plugins=max --without-query-cache"
|
||||
max_configs="$SSL_LIBRARY --with-plugins=max --with-embedded-server --with-libevent --without-plugin=plugin_file_key_management"
|
||||
max_configs="$SSL_LIBRARY --with-plugins=max --with-embedded-server --with-libevent --without-plugin=plugin_file_key_management --with-plugin-rocksdb=dynamic"
|
||||
all_configs="$SSL_LIBRARY --with-plugins=max --with-embedded-server --with-innodb_plugin --with-libevent"
|
||||
|
||||
#
|
||||
|
@ -289,6 +289,11 @@ gcov_compile_flags="-fprofile-arcs -ftest-coverage"
|
|||
gcov_compile_flags="$gcov_compile_flags -DDISABLE_TAO_ASM"
|
||||
gcov_compile_flags="$gcov_compile_flags -DMYSQL_SERVER_SUFFIX=-gcov -DHAVE_gcov"
|
||||
|
||||
#
|
||||
# The following plugins doesn't work on 32 bit systems
|
||||
disable_64_bit_plugins="--without-plugin-tokudb --without-plugin-rocksdb"
|
||||
|
||||
|
||||
# GCC4 needs -fprofile-arcs -ftest-coverage on the linker command line (as well
|
||||
# as on the compiler command line), and this requires setting LDFLAGS for BDB.
|
||||
|
||||
|
|
|
@ -1,25 +0,0 @@
|
|||
#! /bin/sh
|
||||
|
||||
# Copyright (C) 2005, 2006 MySQL AB
|
||||
# Use is subject to license terms
|
||||
# This program is free software; you can redistribute it and/or
|
||||
# modify it under the terms of the GNU Library General Public
|
||||
# License as published by the Free Software Foundation; version 2
|
||||
# of the License.
|
||||
#
|
||||
# This program is distributed in the hope that it will be useful,
|
||||
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
# Library General Public License for more details.
|
||||
#
|
||||
# You should have received a copy of the GNU Library General Public
|
||||
# License along with this library; if not, write to the Free
|
||||
# Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston,
|
||||
# MA 02110-1301, USA
|
||||
|
||||
path=`dirname $0`
|
||||
. "$path/SETUP.sh"
|
||||
extra_flags="$amd64_cflags $debug_cflags"
|
||||
extra_configs="$amd64_configs $debug_configs $max_configs"
|
||||
|
||||
. "$path/FINISH.sh"
|
|
@ -1,7 +0,0 @@
|
|||
#! /bin/sh
|
||||
path=`dirname $0`
|
||||
. "$path/SETUP.sh"
|
||||
extra_flags="$amd64_cflags -pg -g"
|
||||
extra_configs="$amd64_configs $max_configs --disable-shared $static_link"
|
||||
|
||||
. "$path/FINISH.sh"
|
|
@ -20,7 +20,7 @@ path=`dirname $0`
|
|||
. "$path/SETUP.sh"
|
||||
|
||||
extra_flags="$pentium_cflags $fast_cflags"
|
||||
extra_configs="$pentium_configs"
|
||||
extra_configs="$pentium_configs $disable_64_bit_plugins"
|
||||
strip=yes
|
||||
|
||||
. "$path/FINISH.sh"
|
||||
|
|
|
@ -19,6 +19,6 @@ path=`dirname $0`
|
|||
. "$path/SETUP.sh"
|
||||
|
||||
extra_flags="$pentium_cflags $debug_cflags"
|
||||
extra_configs="$pentium_configs $debug_configs"
|
||||
extra_configs="$pentium_configs $debug_configs $disable_64_bit_plugins"
|
||||
|
||||
. "$path/FINISH.sh"
|
||||
|
|
|
@ -5,6 +5,6 @@ set -- "$@" --with-debug=full
|
|||
. "$path/SETUP.sh"
|
||||
|
||||
extra_flags="$pentium_cflags $debug_cflags"
|
||||
extra_configs="$pentium_configs $debug_configs $all_configs $error_inject --with-experimental-collations"
|
||||
extra_configs="$pentium_configs $debug_configs $all_configs $error_inject --with-experimental-collations $disable_64_bit_plugins"
|
||||
|
||||
. "$path/FINISH.sh"
|
||||
|
|
|
@ -19,6 +19,6 @@ path=`dirname $0`
|
|||
. "$path/SETUP.sh"
|
||||
|
||||
extra_flags="$pentium_cflags $debug_cflags"
|
||||
extra_configs="$pentium_configs $debug_configs $max_configs $error_inject --with-experimental-collations"
|
||||
extra_configs="$pentium_configs $debug_configs $max_configs $error_inject --with-experimental-collations $disable_64_bit_plugins"
|
||||
|
||||
. "$path/FINISH.sh"
|
||||
|
|
|
@ -20,6 +20,6 @@ path=`dirname $0`
|
|||
. "$path/SETUP.sh"
|
||||
|
||||
extra_flags="$pentium_cflags $debug_cflags"
|
||||
extra_configs="$pentium_configs $debug_configs $max_no_embedded_configs"
|
||||
extra_configs="$pentium_configs $debug_configs $max_no_embedded_configs $disable_64_bit_plugins"
|
||||
|
||||
. "$path/FINISH.sh"
|
||||
|
|
|
@ -1,24 +0,0 @@
|
|||
#! /bin/sh
|
||||
|
||||
# Copyright (c) 2005, 2010, Oracle and/or its affiliates. All rights reserved.
|
||||
#
|
||||
# This program is free software; you can redistribute it and/or modify
|
||||
# it under the terms of the GNU General Public License as published by
|
||||
# the Free Software Foundation; version 2 of the License.
|
||||
#
|
||||
# This program is distributed in the hope that it will be useful,
|
||||
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
# GNU General Public License for more details.
|
||||
#
|
||||
# You should have received a copy of the GNU General Public License
|
||||
# along with this program; if not, write to the Free Software
|
||||
# Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
|
||||
|
||||
path=`dirname $0`
|
||||
. "$path/SETUP.sh"
|
||||
|
||||
extra_flags="$pentium_cflags $debug_cflags"
|
||||
extra_configs="$pentium_configs $debug_configs $max_configs"
|
||||
|
||||
. "$path/FINISH.sh"
|
|
@ -1,10 +0,0 @@
|
|||
#! /bin/sh
|
||||
# Builds server without query cache support
|
||||
|
||||
path=`dirname $0`
|
||||
. "$path/SETUP.sh"
|
||||
|
||||
extra_flags="$pentium_cflags $debug_cflags"
|
||||
extra_configs="$pentium_configs $debug_configs $max_no_qc_configs"
|
||||
|
||||
. "$path/FINISH.sh"
|
|
@ -19,7 +19,7 @@ path=`dirname $0`
|
|||
. "$path/SETUP.sh"
|
||||
|
||||
extra_flags="$pentium_cflags $debug_cflags"
|
||||
extra_configs="$pentium_configs $debug_configs"
|
||||
extra_configs="$pentium_configs $debug_configs $disable_64_bit_plugins"
|
||||
|
||||
extra_configs="$extra_configs --with-debug --with-ssl=/usr"
|
||||
|
||||
|
|
|
@ -7,6 +7,6 @@ set -- "$@" --with-debug=full
|
|||
extra_flags="$pentium_cflags $debug_cflags -g -O0 $wsrep_cflags"
|
||||
c_warnings="$c_warnings $debug_extra_warnings"
|
||||
cxx_warnings="$cxx_warnings $debug_extra_warnings"
|
||||
extra_configs="$pentium_configs $debug_configs $wsrep_configs --with-wsrep"
|
||||
extra_configs="$pentium_configs $debug_configs $wsrep_configs --with-wsrep $disable_64_bit_plugins"
|
||||
|
||||
. "$path/FINISH.sh"
|
||||
|
|
|
@ -40,6 +40,6 @@ export LDFLAGS="$gcov_link_flags"
|
|||
extra_flags="$pentium_cflags $debug_cflags $max_cflags $gcov_compile_flags"
|
||||
c_warnings="$c_warnings $debug_extra_warnings"
|
||||
cxx_warnings="$cxx_warnings $debug_extra_warnings"
|
||||
extra_configs="$pentium_configs $debug_configs $gcov_configs $max_configs"
|
||||
extra_configs="$pentium_configs $debug_configs $gcov_configs $max_configs $disable_64_bit_plugins"
|
||||
|
||||
. "$path/FINISH.sh"
|
||||
|
|
|
@ -19,6 +19,6 @@ path=`dirname $0`
|
|||
. "$path/SETUP.sh"
|
||||
|
||||
extra_flags="$pentium_cflags $gprof_compile_flags"
|
||||
extra_configs="$pentium_configs $debug_configs $gprof_link_flags"
|
||||
extra_configs="$pentium_configs $debug_configs $gprof_link_flags $disable_64_bit_plugins"
|
||||
|
||||
. "$path/FINISH.sh"
|
||||
|
|
|
@ -35,6 +35,6 @@ extra_flags="$fast_cflags -unroll2 -ip -mp -restrict"
|
|||
# icpc: error: problem during multi-file optimization compilation (code 1)
|
||||
extra_flags="$extra_flags -no-ipo"
|
||||
base_cxxflags="-fno-exceptions -fno-rtti"
|
||||
extra_configs="$pentium_configs $static_link"
|
||||
extra_configs="$pentium_configs $static_link $disable_64_bit_plugins"
|
||||
|
||||
. "$path/FINISH.sh"
|
||||
|
|
|
@ -20,6 +20,6 @@ path=`dirname $0`
|
|||
. "$path/SETUP.sh"
|
||||
|
||||
extra_flags="$pentium_cflags $fast_cflags -g"
|
||||
extra_configs="$pentium_configs $max_configs"
|
||||
extra_configs="$pentium_configs $max_configs $disable_64_bit_plugins"
|
||||
|
||||
. "$path/FINISH.sh"
|
||||
|
|
|
@ -33,6 +33,6 @@ path=`dirname $0`
|
|||
. "$path/SETUP.sh"
|
||||
|
||||
extra_flags="$pentium_cflags $debug_cflags $valgrind_flags"
|
||||
extra_configs="$pentium_configs $debug_configs $valgrind_configs $max_configs"
|
||||
extra_configs="$pentium_configs $debug_configs $valgrind_configs $max_configs $disable_64_bit_plugins"
|
||||
|
||||
. "$path/FINISH.sh"
|
||||
|
|
|
@ -1,26 +0,0 @@
|
|||
#! /bin/sh
|
||||
|
||||
# Copyright (c) 2008, 2010, Oracle and/or its affiliates. All rights reserved.
|
||||
#
|
||||
# This program is free software; you can redistribute it and/or
|
||||
# modify it under the terms of the GNU Library General Public
|
||||
# License as published by the Free Software Foundation; version 2
|
||||
# of the License.
|
||||
#
|
||||
# This program is distributed in the hope that it will be useful,
|
||||
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
# Library General Public License for more details.
|
||||
#
|
||||
# You should have received a copy of the GNU Library General Public
|
||||
# License along with this library; if not, write to the Free
|
||||
# Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston,
|
||||
# MA 02110-1301, USA
|
||||
|
||||
path=`dirname $0`
|
||||
. "$path/SETUP.sh"
|
||||
|
||||
extra_flags="$pentium_cflags $debug_cflags $valgrind_flags"
|
||||
extra_configs="$pentium_configs $debug_configs $valgrind_configs $max_configs"
|
||||
|
||||
. "$path/FINISH.sh"
|
|
@ -4,7 +4,7 @@ path=`dirname $0`
|
|||
. "$path/SETUP.sh"
|
||||
|
||||
extra_flags="$pentium_cflags $fast_cflags $wsrep_cflags"
|
||||
extra_configs="$pentium_configs $wsrep_configs --with-wsrep"
|
||||
extra_configs="$pentium_configs $wsrep_configs --with-wsrep $disable_64_bit_plugins"
|
||||
|
||||
#strip=yes
|
||||
|
||||
|
|
|
@ -1,25 +0,0 @@
|
|||
#! /bin/sh
|
||||
|
||||
# Copyright (c) 2005, 2006 MySQL AB
|
||||
# Use is subject to license terms
|
||||
#
|
||||
# This program is free software; you can redistribute it and/or modify
|
||||
# it under the terms of the GNU General Public License as published by
|
||||
# the Free Software Foundation; version 2 of the License.
|
||||
#
|
||||
# This program is distributed in the hope that it will be useful,
|
||||
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
# GNU General Public License for more details.
|
||||
#
|
||||
# You should have received a copy of the GNU General Public License
|
||||
# along with this program; if not, write to the Free Software
|
||||
# Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
|
||||
|
||||
path=`dirname $0`
|
||||
. "$path/SETUP.sh"
|
||||
|
||||
extra_flags="$ppc_cflags $debug_cflags"
|
||||
extra_configs="$debug_configs $max_configs"
|
||||
|
||||
. "$path/FINISH.sh"
|
|
@ -1,5 +1,5 @@
|
|||
# Copyright (c) 2006, 2014, Oracle and/or its affiliates.
|
||||
# Copyright (c) 2008, 2014, Monty Program Ab
|
||||
# Copyright (c) 2006, 2017, Oracle and/or its affiliates.
|
||||
# Copyright (c) 2008, 2017, MariaDB
|
||||
#
|
||||
# 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
|
||||
|
@ -220,11 +220,9 @@ IF(SECURITY_HARDENED)
|
|||
MY_CHECK_AND_SET_COMPILER_FLAG("-D_FORTIFY_SOURCE=2" RELEASE RELWITHDEBINFO)
|
||||
ENDIF()
|
||||
|
||||
OPTION(ENABLE_DEBUG_SYNC "Enable debug sync (debug builds only)" ON)
|
||||
IF(ENABLE_DEBUG_SYNC)
|
||||
SET(CMAKE_CXX_FLAGS_DEBUG "${CMAKE_CXX_FLAGS_DEBUG} -DENABLED_DEBUG_SYNC")
|
||||
SET(CMAKE_C_FLAGS_DEBUG "${CMAKE_C_FLAGS_DEBUG} -DENABLED_DEBUG_SYNC")
|
||||
ENDIF()
|
||||
# Always enable debug sync for debug builds.
|
||||
SET(CMAKE_CXX_FLAGS_DEBUG "${CMAKE_CXX_FLAGS_DEBUG} -DENABLED_DEBUG_SYNC")
|
||||
SET(CMAKE_C_FLAGS_DEBUG "${CMAKE_C_FLAGS_DEBUG} -DENABLED_DEBUG_SYNC")
|
||||
|
||||
OPTION(ENABLE_GCOV "Enable gcov (debug, Linux builds only)" OFF)
|
||||
IF (ENABLE_GCOV)
|
||||
|
@ -365,7 +363,7 @@ ENDIF()
|
|||
|
||||
SET (MYSQLD_STATIC_PLUGIN_LIBS "" CACHE INTERNAL "")
|
||||
|
||||
# mariadb_connector_c fetches submodules which is useful for plugins
|
||||
INCLUDE(submodules)
|
||||
INCLUDE(mariadb_connector_c) # this does ADD_SUBDIRECTORY(libmariadb)
|
||||
|
||||
# Add storage engines and plugins.
|
||||
|
@ -462,7 +460,6 @@ INSTALL_DOCUMENTATION(README.md CREDITS COPYING COPYING.thirdparty
|
|||
# ${CMAKE_BINARY_DIR}/Docs/INFO_BIN)
|
||||
|
||||
IF(UNIX)
|
||||
INSTALL_DOCUMENTATION(Docs/INSTALL-BINARY COMPONENT Readme)
|
||||
INSTALL_DOCUMENTATION(Docs/INSTALL-BINARY Docs/README-wsrep COMPONENT Readme)
|
||||
ENDIF()
|
||||
|
||||
|
|
24
CREDITS
24
CREDITS
|
@ -4,17 +4,19 @@ organization registered in the USA.
|
|||
The current main sponsors of the MariaDB Foundation are:
|
||||
|
||||
Alibaba Cloud https://intl.aliyun.com (2017)
|
||||
Booking.com https://www.booking.com (2013 - 2017)
|
||||
Development Bank of Singapore https://dbs.com (2016 - 2017)
|
||||
MariaDB Corporation https://www.mariadb.com (2013 - 2017)
|
||||
Visma https://visma.com (2015 - 2017)
|
||||
Acronis http://acronis.com (2016 - 2017)
|
||||
Nexedi https://www.nexedi.com (2016 - 2017)
|
||||
Automattic https://automattic.com (2014 - 2017)
|
||||
Tencent Game DBA http://tencentdba.com/about (2016 - 2017)
|
||||
Tencent TDSQL http://tdsql.org/ (2016 - 2017)
|
||||
Verkkokauppa.com https://www.verkkokauppa.com (2015 - 2017)
|
||||
Virtuozzo https://virtuozzo.com (2016 - 2017)
|
||||
Booking.com https://www.booking.com (2013)
|
||||
Tencent Cloud https://cloud.tencent.com (2017)
|
||||
Development Bank of Singapore https://dbs.com (2016)
|
||||
IBM https://www.ibm.com (2017)
|
||||
MariaDB Corporation https://www.mariadb.com (2013)
|
||||
Visma https://visma.com (2015)
|
||||
Acronis http://acronis.com (2016)
|
||||
Nexedi https://www.nexedi.com (2016)
|
||||
Automattic https://automattic.com (2014)
|
||||
Tencent Game DBA http://tencentdba.com/about (2016)
|
||||
Tencent TDSQL http://tdsql.org (2016)
|
||||
Verkkokauppa.com https://www.verkkokauppa.com (2015)
|
||||
Virtuozzo https://virtuozzo.com (2016)
|
||||
|
||||
For a full list of sponsors, see
|
||||
https://mariadb.org/about/supporters/
|
||||
|
|
|
@ -8,7 +8,7 @@ Please read the CREDITS file for details about the MariaDB Foundation,
|
|||
and who is developing MariaDB.
|
||||
|
||||
MariaDB is developed by many of the original developers of MySQL who
|
||||
now work for the MariadB Foundation and the MariaDB Corporation, and by many people in
|
||||
now work for the MariaDB Foundation and the MariaDB Corporation, and by many people in
|
||||
the community.
|
||||
|
||||
MySQL, which is the base of MariaDB, is a product and trademark of Oracle
|
||||
|
|
2
VERSION
2
VERSION
|
@ -1,3 +1,3 @@
|
|||
MYSQL_VERSION_MAJOR=10
|
||||
MYSQL_VERSION_MINOR=2
|
||||
MYSQL_VERSION_PATCH=6
|
||||
MYSQL_VERSION_PATCH=9
|
||||
|
|
|
@ -120,4 +120,3 @@ enum options_client
|
|||
Name of the performance schema database.
|
||||
*/
|
||||
#define PERFORMANCE_SCHEMA_DB_NAME "performance_schema"
|
||||
|
||||
|
|
110
client/mysql.cc
110
client/mysql.cc
|
@ -1,6 +1,6 @@
|
|||
/*
|
||||
Copyright (c) 2000, 2014, Oracle and/or its affiliates.
|
||||
Copyright (c) 2009, 2016, MariaDB
|
||||
Copyright (c) 2009, 2017, MariaDB
|
||||
|
||||
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
|
||||
|
@ -149,7 +149,7 @@ static my_bool ignore_errors=0,wait_flag=0,quick=0,
|
|||
default_pager_set= 0, opt_sigint_ignore= 0,
|
||||
auto_vertical_output= 0,
|
||||
show_warnings= 0, executing_query= 0,
|
||||
ignore_spaces= 0, opt_progress_reports;
|
||||
ignore_spaces= 0, opt_binhex= 0, opt_progress_reports;
|
||||
static my_bool debug_info_flag, debug_check_flag, batch_abort_on_error;
|
||||
static my_bool column_types_flag;
|
||||
static my_bool preserve_comments= 0;
|
||||
|
@ -1145,8 +1145,6 @@ int main(int argc,char *argv[])
|
|||
outfile[0]=0; // no (default) outfile
|
||||
strmov(pager, "stdout"); // the default, if --pager wasn't given
|
||||
|
||||
mysql_init(&mysql);
|
||||
|
||||
{
|
||||
char *tmp=getenv("PAGER");
|
||||
if (tmp && strlen(tmp))
|
||||
|
@ -1185,7 +1183,11 @@ int main(int argc,char *argv[])
|
|||
}
|
||||
defaults_argv=argv;
|
||||
if ((status.exit_status= get_options(argc, (char **) argv)))
|
||||
mysql_end(-1);
|
||||
{
|
||||
free_defaults(defaults_argv);
|
||||
my_end(0);
|
||||
exit(status.exit_status);
|
||||
}
|
||||
|
||||
if (status.batch && !status.line_buff &&
|
||||
!(status.line_buff= batch_readline_init(MAX_BATCH_BUFFER_SIZE, stdin)))
|
||||
|
@ -1494,6 +1496,8 @@ static struct my_option my_long_options[] =
|
|||
{"batch", 'B',
|
||||
"Don't use history file. Disable interactive behavior. (Enables --silent.)",
|
||||
0, 0, 0, GET_NO_ARG, NO_ARG, 0, 0, 0, 0, 0, 0},
|
||||
{"binary-as-hex", 'b', "Print binary data as hex", &opt_binhex, &opt_binhex,
|
||||
0, GET_BOOL, NO_ARG, 0, 0, 0, 0, 0, 0},
|
||||
{"character-sets-dir", OPT_CHARSETS_DIR,
|
||||
"Directory for character set files.", &charsets_dir,
|
||||
&charsets_dir, 0, GET_STR, REQUIRED_ARG, 0, 0, 0, 0, 0, 0},
|
||||
|
@ -2321,8 +2325,10 @@ static bool add_line(String &buffer, char *line, ulong line_length,
|
|||
continue;
|
||||
}
|
||||
#endif
|
||||
if (!*ml_comment && inchar == '\\' &&
|
||||
!(*in_string &&
|
||||
if (!*ml_comment && inchar == '\\' && *in_string != '`' &&
|
||||
!(*in_string == '"' &&
|
||||
(mysql.server_status & SERVER_STATUS_ANSI_QUOTES)) &&
|
||||
!(*in_string &&
|
||||
(mysql.server_status & SERVER_STATUS_NO_BACKSLASH_ESCAPES)))
|
||||
{
|
||||
// Found possbile one character command like \c
|
||||
|
@ -3061,7 +3067,6 @@ static int com_server_help(String *buffer __attribute__((unused)),
|
|||
{
|
||||
unsigned int num_fields= mysql_num_fields(result);
|
||||
my_ulonglong num_rows= mysql_num_rows(result);
|
||||
mysql_fetch_fields(result);
|
||||
if (num_fields==3 && num_rows==1)
|
||||
{
|
||||
if (!(cur= mysql_fetch_row(result)))
|
||||
|
@ -3315,7 +3320,8 @@ com_go(String *buffer,char *line __attribute__((unused)))
|
|||
print_table_data_html(result);
|
||||
else if (opt_xml)
|
||||
print_table_data_xml(result);
|
||||
else if (vertical || (auto_vertical_output && (terminal_width < get_result_width(result))))
|
||||
else if (vertical || (auto_vertical_output &&
|
||||
(terminal_width < get_result_width(result))))
|
||||
print_table_data_vertically(result);
|
||||
else if (opt_silent && verbose <= 2 && !output_tables)
|
||||
print_tab_data(result);
|
||||
|
@ -3533,6 +3539,41 @@ print_field_types(MYSQL_RES *result)
|
|||
}
|
||||
|
||||
|
||||
/* Used to determine if we should invoke print_as_hex for this field */
|
||||
|
||||
static bool
|
||||
is_binary_field(MYSQL_FIELD *field)
|
||||
{
|
||||
if ((field->charsetnr == 63) &&
|
||||
(field->type == MYSQL_TYPE_BIT ||
|
||||
field->type == MYSQL_TYPE_BLOB ||
|
||||
field->type == MYSQL_TYPE_LONG_BLOB ||
|
||||
field->type == MYSQL_TYPE_MEDIUM_BLOB ||
|
||||
field->type == MYSQL_TYPE_TINY_BLOB ||
|
||||
field->type == MYSQL_TYPE_VAR_STRING ||
|
||||
field->type == MYSQL_TYPE_STRING ||
|
||||
field->type == MYSQL_TYPE_VARCHAR ||
|
||||
field->type == MYSQL_TYPE_GEOMETRY))
|
||||
return 1;
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
/* Print binary value as hex literal (0x ...) */
|
||||
|
||||
static void
|
||||
print_as_hex(FILE *output_file, const char *str, ulong len, ulong total_bytes_to_send)
|
||||
{
|
||||
const char *ptr= str, *end= ptr+len;
|
||||
ulong i;
|
||||
fprintf(output_file, "0x");
|
||||
for(; ptr < end; ptr++)
|
||||
fprintf(output_file, "%02X", *((uchar*)ptr));
|
||||
for (i= 2*len+2; i < total_bytes_to_send; i++)
|
||||
tee_putc((int)' ', output_file);
|
||||
}
|
||||
|
||||
|
||||
static void
|
||||
print_table_data(MYSQL_RES *result)
|
||||
{
|
||||
|
@ -3559,6 +3600,8 @@ print_table_data(MYSQL_RES *result)
|
|||
length= MY_MAX(length,field->max_length);
|
||||
if (length < 4 && !IS_NOT_NULL(field->flags))
|
||||
length=4; // Room for "NULL"
|
||||
if (opt_binhex && is_binary_field(field))
|
||||
length= 2 + length * 2;
|
||||
field->max_length=length;
|
||||
num_flag[mysql_field_tell(result) - 1]= IS_NUM(field->type);
|
||||
separator.fill(separator.length()+length+2,'-');
|
||||
|
@ -3626,9 +3669,11 @@ print_table_data(MYSQL_RES *result)
|
|||
many extra padding-characters we should send with the printing function.
|
||||
*/
|
||||
visible_length= charset_info->cset->numcells(charset_info, buffer, buffer + data_length);
|
||||
extra_padding= data_length - visible_length;
|
||||
extra_padding= (uint) (data_length - visible_length);
|
||||
|
||||
if (field_max_length > MAX_COLUMN_LENGTH)
|
||||
if (opt_binhex && is_binary_field(field))
|
||||
print_as_hex(PAGER, cur[off], lengths[off], field_max_length);
|
||||
else if (field_max_length > MAX_COLUMN_LENGTH)
|
||||
tee_print_sized_data(buffer, data_length, MAX_COLUMN_LENGTH+extra_padding, FALSE);
|
||||
else
|
||||
{
|
||||
|
@ -3762,11 +3807,15 @@ print_table_data_html(MYSQL_RES *result)
|
|||
if (interrupted_query)
|
||||
break;
|
||||
ulong *lengths=mysql_fetch_lengths(result);
|
||||
field= mysql_fetch_fields(result);
|
||||
(void) tee_fputs("<TR>", PAGER);
|
||||
for (uint i=0; i < mysql_num_fields(result); i++)
|
||||
{
|
||||
(void) tee_fputs("<TD>", PAGER);
|
||||
xmlencode_print(cur[i], lengths[i]);
|
||||
if (opt_binhex && is_binary_field(&field[i]))
|
||||
print_as_hex(PAGER, cur[i], lengths[i], lengths[i]);
|
||||
else
|
||||
xmlencode_print(cur[i], lengths[i]);
|
||||
(void) tee_fputs("</TD>", PAGER);
|
||||
}
|
||||
(void) tee_fputs("</TR>", PAGER);
|
||||
|
@ -3802,7 +3851,10 @@ print_table_data_xml(MYSQL_RES *result)
|
|||
if (cur[i])
|
||||
{
|
||||
tee_fprintf(PAGER, "\">");
|
||||
xmlencode_print(cur[i], lengths[i]);
|
||||
if (opt_binhex && is_binary_field(&fields[i]))
|
||||
print_as_hex(PAGER, cur[i], lengths[i], lengths[i]);
|
||||
else
|
||||
xmlencode_print(cur[i], lengths[i]);
|
||||
tee_fprintf(PAGER, "</field>\n");
|
||||
}
|
||||
else
|
||||
|
@ -3849,13 +3901,19 @@ print_table_data_vertically(MYSQL_RES *result)
|
|||
{
|
||||
unsigned int i;
|
||||
const char *p;
|
||||
|
||||
if (opt_binhex && is_binary_field(field))
|
||||
fprintf(PAGER, "0x");
|
||||
for (i= 0, p= cur[off]; i < lengths[off]; i+= 1, p+= 1)
|
||||
{
|
||||
if (*p == '\0')
|
||||
tee_putc((int)' ', PAGER);
|
||||
if (opt_binhex && is_binary_field(field))
|
||||
fprintf(PAGER, "%02X", *((uchar*)p));
|
||||
else
|
||||
tee_putc((int)*p, PAGER);
|
||||
{
|
||||
if (*p == '\0')
|
||||
tee_putc((int)' ', PAGER);
|
||||
else
|
||||
tee_putc((int)*p, PAGER);
|
||||
}
|
||||
}
|
||||
tee_putc('\n', PAGER);
|
||||
}
|
||||
|
@ -3865,7 +3923,6 @@ print_table_data_vertically(MYSQL_RES *result)
|
|||
}
|
||||
}
|
||||
|
||||
|
||||
/* print_warnings should be called right after executing a statement */
|
||||
|
||||
static void print_warnings()
|
||||
|
@ -4002,11 +4059,19 @@ print_tab_data(MYSQL_RES *result)
|
|||
while ((cur = mysql_fetch_row(result)))
|
||||
{
|
||||
lengths=mysql_fetch_lengths(result);
|
||||
safe_put_field(cur[0],lengths[0]);
|
||||
field= mysql_fetch_fields(result);
|
||||
if (opt_binhex && is_binary_field(&field[0]))
|
||||
print_as_hex(PAGER, cur[0], lengths[0], lengths[0]);
|
||||
else
|
||||
safe_put_field(cur[0],lengths[0]);
|
||||
|
||||
for (uint off=1 ; off < mysql_num_fields(result); off++)
|
||||
{
|
||||
(void) tee_fputs("\t", PAGER);
|
||||
safe_put_field(cur[off], lengths[off]);
|
||||
if (opt_binhex && field && is_binary_field(&field[off]))
|
||||
print_as_hex(PAGER, cur[off], lengths[off], lengths[off]);
|
||||
else
|
||||
safe_put_field(cur[off], lengths[off]);
|
||||
}
|
||||
(void) tee_fputs("\n", PAGER);
|
||||
}
|
||||
|
@ -4802,10 +4867,11 @@ com_status(String *buffer __attribute__((unused)),
|
|||
tee_fprintf(stdout, "Protocol:\t\tCompressed\n");
|
||||
#endif
|
||||
|
||||
if ((status_str= mysql_stat(&mysql)) && !mysql_error(&mysql)[0])
|
||||
const char *pos;
|
||||
if ((status_str= mysql_stat(&mysql)) && !mysql_error(&mysql)[0] &&
|
||||
(pos= strchr(status_str,' ')))
|
||||
{
|
||||
ulong sec;
|
||||
const char *pos= strchr(status_str,' ');
|
||||
/* print label */
|
||||
tee_fprintf(stdout, "%.*s\t\t\t", (int) (pos-status_str), status_str);
|
||||
if ((status_str= str2int(pos,10,0,LONG_MAX,(long*) &sec)))
|
||||
|
|
|
@ -1,6 +1,6 @@
|
|||
/*
|
||||
Copyright (c) 2006, 2013, Oracle and/or its affiliates.
|
||||
Copyright (c) 2010, 2016, MariaDB
|
||||
Copyright (c) 2010, 2017, MariaDB
|
||||
|
||||
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
|
||||
|
@ -1130,7 +1130,7 @@ static int check_version_match(void)
|
|||
|
||||
int main(int argc, char **argv)
|
||||
{
|
||||
char self_name[FN_REFLEN];
|
||||
char self_name[FN_REFLEN + 1];
|
||||
|
||||
MY_INIT(argv[0]);
|
||||
|
||||
|
@ -1138,7 +1138,7 @@ int main(int argc, char **argv)
|
|||
if (GetModuleFileName(NULL, self_name, FN_REFLEN) == 0)
|
||||
#endif
|
||||
{
|
||||
strncpy(self_name, argv[0], FN_REFLEN);
|
||||
strmake_buf(self_name, argv[0]);
|
||||
}
|
||||
|
||||
if (init_dynamic_string(&ds_args, "", 512, 256) ||
|
||||
|
@ -1171,6 +1171,8 @@ int main(int argc, char **argv)
|
|||
{
|
||||
int fd= create_temp_file(cnf_file_path, opt_tmpdir[0] ? opt_tmpdir : NULL,
|
||||
"mysql_upgrade-", O_CREAT | O_WRONLY, MYF(MY_FAE));
|
||||
if (fd < 0)
|
||||
die(NULL);
|
||||
my_write(fd, USTRING_WITH_LEN( "[client]\n"), MYF(MY_FAE));
|
||||
my_write(fd, (uchar*)ds_args.str, ds_args.length, MYF(MY_FAE));
|
||||
my_close(fd, MYF(0));
|
||||
|
|
|
@ -1,6 +1,6 @@
|
|||
/*
|
||||
Copyright (c) 2000, 2014, Oracle and/or its affiliates.
|
||||
Copyright (c) 2010, 2016, MariaDB
|
||||
Copyright (c) 2010, 2017, MariaDB
|
||||
|
||||
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
|
||||
|
@ -47,6 +47,7 @@ static uint opt_count_iterations= 0, my_end_arg;
|
|||
static ulong opt_connect_timeout, opt_shutdown_timeout;
|
||||
static char * unix_port=0;
|
||||
static char *opt_plugin_dir= 0, *opt_default_auth= 0;
|
||||
static bool sql_log_bin_off= false;
|
||||
|
||||
#ifdef HAVE_SMEM
|
||||
static char *shared_memory_base_name=0;
|
||||
|
@ -600,6 +601,31 @@ static my_bool sql_connect(MYSQL *mysql, uint wait)
|
|||
}
|
||||
|
||||
|
||||
static int maybe_disable_binlog(MYSQL *mysql)
|
||||
{
|
||||
if (opt_local && !sql_log_bin_off)
|
||||
{
|
||||
if (mysql_query(mysql, "set local sql_log_bin=0"))
|
||||
{
|
||||
my_printf_error(0, "SET LOCAL SQL_LOG_BIN=0 failed; error: '%-.200s'",
|
||||
error_flags, mysql_error(mysql));
|
||||
return -1;
|
||||
}
|
||||
}
|
||||
sql_log_bin_off= true;
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
int flush(MYSQL *mysql, const char *what)
|
||||
{
|
||||
char buf[FN_REFLEN];
|
||||
my_snprintf(buf, sizeof(buf), "flush %s%s",
|
||||
(opt_local && !sql_log_bin_off ? "local " : ""), what);
|
||||
return mysql_query(mysql, buf);
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
@brief Execute all commands
|
||||
|
||||
|
@ -616,6 +642,7 @@ static my_bool sql_connect(MYSQL *mysql, uint wait)
|
|||
|
||||
static int execute_commands(MYSQL *mysql,int argc, char **argv)
|
||||
{
|
||||
int ret = 0;
|
||||
const char *status;
|
||||
/*
|
||||
MySQL documentation relies on the fact that mysqladmin will
|
||||
|
@ -628,17 +655,6 @@ static int execute_commands(MYSQL *mysql,int argc, char **argv)
|
|||
struct my_rnd_struct rand_st;
|
||||
char buff[FN_REFLEN + 20];
|
||||
|
||||
if (opt_local)
|
||||
{
|
||||
sprintf(buff, "set local sql_log_bin=0");
|
||||
if (mysql_query(mysql, buff))
|
||||
{
|
||||
my_printf_error(0, "SET LOCAL SQL_LOG_BIN=0 failed; error: '%-.200s'",
|
||||
error_flags, mysql_error(mysql));
|
||||
return -1;
|
||||
}
|
||||
}
|
||||
|
||||
for (; argc > 0 ; argv++,argc--)
|
||||
{
|
||||
int command;
|
||||
|
@ -650,6 +666,8 @@ static int execute_commands(MYSQL *mysql,int argc, char **argv)
|
|||
my_printf_error(0, "Too few arguments to create", error_flags);
|
||||
return 1;
|
||||
}
|
||||
if (maybe_disable_binlog(mysql))
|
||||
return -1;
|
||||
sprintf(buff,"create database `%.*s`",FN_REFLEN,argv[1]);
|
||||
if (mysql_query(mysql,buff))
|
||||
{
|
||||
|
@ -667,6 +685,8 @@ static int execute_commands(MYSQL *mysql,int argc, char **argv)
|
|||
my_printf_error(0, "Too few arguments to drop", error_flags);
|
||||
return 1;
|
||||
}
|
||||
if (maybe_disable_binlog(mysql))
|
||||
return -1;
|
||||
if (drop_db(mysql,argv[1]))
|
||||
return -1;
|
||||
argc--; argv++;
|
||||
|
@ -707,7 +727,7 @@ static int execute_commands(MYSQL *mysql,int argc, char **argv)
|
|||
}
|
||||
case ADMIN_FLUSH_PRIVILEGES:
|
||||
case ADMIN_RELOAD:
|
||||
if (mysql_query(mysql,"flush privileges"))
|
||||
if (flush(mysql, "privileges"))
|
||||
{
|
||||
my_printf_error(0, "reload failed; error: '%s'", error_flags,
|
||||
mysql_error(mysql));
|
||||
|
@ -911,7 +931,7 @@ static int execute_commands(MYSQL *mysql,int argc, char **argv)
|
|||
}
|
||||
case ADMIN_FLUSH_LOGS:
|
||||
{
|
||||
if (mysql_query(mysql,"flush logs"))
|
||||
if (flush(mysql, "logs"))
|
||||
{
|
||||
my_printf_error(0, "flush failed; error: '%s'", error_flags,
|
||||
mysql_error(mysql));
|
||||
|
@ -921,7 +941,7 @@ static int execute_commands(MYSQL *mysql,int argc, char **argv)
|
|||
}
|
||||
case ADMIN_FLUSH_BINARY_LOG:
|
||||
{
|
||||
if (mysql_query(mysql, "flush binary logs"))
|
||||
if (flush(mysql, "binary logs"))
|
||||
{
|
||||
my_printf_error(0, "flush failed; error: '%s'", error_flags,
|
||||
mysql_error(mysql));
|
||||
|
@ -931,7 +951,7 @@ static int execute_commands(MYSQL *mysql,int argc, char **argv)
|
|||
}
|
||||
case ADMIN_FLUSH_ENGINE_LOG:
|
||||
{
|
||||
if (mysql_query(mysql,"flush engine logs"))
|
||||
if (flush(mysql, "engine logs"))
|
||||
{
|
||||
my_printf_error(0, "flush failed; error: '%s'", error_flags,
|
||||
mysql_error(mysql));
|
||||
|
@ -941,7 +961,7 @@ static int execute_commands(MYSQL *mysql,int argc, char **argv)
|
|||
}
|
||||
case ADMIN_FLUSH_ERROR_LOG:
|
||||
{
|
||||
if (mysql_query(mysql, "flush error logs"))
|
||||
if (flush(mysql, "error logs"))
|
||||
{
|
||||
my_printf_error(0, "flush failed; error: '%s'", error_flags,
|
||||
mysql_error(mysql));
|
||||
|
@ -951,7 +971,7 @@ static int execute_commands(MYSQL *mysql,int argc, char **argv)
|
|||
}
|
||||
case ADMIN_FLUSH_GENERAL_LOG:
|
||||
{
|
||||
if (mysql_query(mysql, "flush general logs"))
|
||||
if (flush(mysql, "general logs"))
|
||||
{
|
||||
my_printf_error(0, "flush failed; error: '%s'", error_flags,
|
||||
mysql_error(mysql));
|
||||
|
@ -961,7 +981,7 @@ static int execute_commands(MYSQL *mysql,int argc, char **argv)
|
|||
}
|
||||
case ADMIN_FLUSH_RELAY_LOG:
|
||||
{
|
||||
if (mysql_query(mysql, "flush relay logs"))
|
||||
if (flush(mysql, "relay logs"))
|
||||
{
|
||||
my_printf_error(0, "flush failed; error: '%s'", error_flags,
|
||||
mysql_error(mysql));
|
||||
|
@ -971,7 +991,7 @@ static int execute_commands(MYSQL *mysql,int argc, char **argv)
|
|||
}
|
||||
case ADMIN_FLUSH_SLOW_LOG:
|
||||
{
|
||||
if (mysql_query(mysql,"flush slow logs"))
|
||||
if (flush(mysql, "slow logs"))
|
||||
{
|
||||
my_printf_error(0, "flush failed; error: '%s'", error_flags,
|
||||
mysql_error(mysql));
|
||||
|
@ -981,7 +1001,7 @@ static int execute_commands(MYSQL *mysql,int argc, char **argv)
|
|||
}
|
||||
case ADMIN_FLUSH_HOSTS:
|
||||
{
|
||||
if (mysql_query(mysql,"flush hosts"))
|
||||
if (flush(mysql, "hosts"))
|
||||
{
|
||||
my_printf_error(0, "flush failed; error: '%s'", error_flags,
|
||||
mysql_error(mysql));
|
||||
|
@ -991,7 +1011,7 @@ static int execute_commands(MYSQL *mysql,int argc, char **argv)
|
|||
}
|
||||
case ADMIN_FLUSH_TABLES:
|
||||
{
|
||||
if (mysql_query(mysql,"flush tables"))
|
||||
if (flush(mysql, "tables"))
|
||||
{
|
||||
my_printf_error(0, "flush failed; error: '%s'", error_flags,
|
||||
mysql_error(mysql));
|
||||
|
@ -1001,7 +1021,7 @@ static int execute_commands(MYSQL *mysql,int argc, char **argv)
|
|||
}
|
||||
case ADMIN_FLUSH_STATUS:
|
||||
{
|
||||
if (mysql_query(mysql,"flush status"))
|
||||
if (flush(mysql, "status"))
|
||||
{
|
||||
my_printf_error(0, "flush failed; error: '%s'", error_flags,
|
||||
mysql_error(mysql));
|
||||
|
@ -1011,7 +1031,7 @@ static int execute_commands(MYSQL *mysql,int argc, char **argv)
|
|||
}
|
||||
case ADMIN_FLUSH_TABLE_STATISTICS:
|
||||
{
|
||||
if (mysql_query(mysql,"flush table_statistics"))
|
||||
if (flush(mysql, "table_statistics"))
|
||||
{
|
||||
my_printf_error(0, "flush failed; error: '%s'", error_flags,
|
||||
mysql_error(mysql));
|
||||
|
@ -1021,7 +1041,7 @@ static int execute_commands(MYSQL *mysql,int argc, char **argv)
|
|||
}
|
||||
case ADMIN_FLUSH_INDEX_STATISTICS:
|
||||
{
|
||||
if (mysql_query(mysql,"flush index_statistics"))
|
||||
if (flush(mysql, "index_statistics"))
|
||||
{
|
||||
my_printf_error(0, "flush failed; error: '%s'", error_flags,
|
||||
mysql_error(mysql));
|
||||
|
@ -1031,7 +1051,7 @@ static int execute_commands(MYSQL *mysql,int argc, char **argv)
|
|||
}
|
||||
case ADMIN_FLUSH_USER_STATISTICS:
|
||||
{
|
||||
if (mysql_query(mysql,"flush user_statistics"))
|
||||
if (flush(mysql, "user_statistics"))
|
||||
{
|
||||
my_printf_error(0, "flush failed; error: '%s'", error_flags,
|
||||
mysql_error(mysql));
|
||||
|
@ -1041,7 +1061,7 @@ static int execute_commands(MYSQL *mysql,int argc, char **argv)
|
|||
}
|
||||
case ADMIN_FLUSH_USER_RESOURCES:
|
||||
{
|
||||
if (mysql_query(mysql, "flush user_resources"))
|
||||
if (flush(mysql, "user_resources"))
|
||||
{
|
||||
my_printf_error(0, "flush failed; error: '%s'", error_flags,
|
||||
mysql_error(mysql));
|
||||
|
@ -1051,7 +1071,7 @@ static int execute_commands(MYSQL *mysql,int argc, char **argv)
|
|||
}
|
||||
case ADMIN_FLUSH_CLIENT_STATISTICS:
|
||||
{
|
||||
if (mysql_query(mysql,"flush client_statistics"))
|
||||
if (flush(mysql, "client_statistics"))
|
||||
{
|
||||
my_printf_error(0, "flush failed; error: '%s'", error_flags,
|
||||
mysql_error(mysql));
|
||||
|
@ -1061,9 +1081,8 @@ static int execute_commands(MYSQL *mysql,int argc, char **argv)
|
|||
}
|
||||
case ADMIN_FLUSH_ALL_STATISTICS:
|
||||
{
|
||||
if (mysql_query(mysql,
|
||||
"flush table_statistics,index_statistics,"
|
||||
"user_statistics,client_statistics"))
|
||||
if (flush(mysql, "table_statistics,index_statistics,"
|
||||
"user_statistics,client_statistics"))
|
||||
{
|
||||
my_printf_error(0, "flush failed; error: '%s'", error_flags,
|
||||
mysql_error(mysql));
|
||||
|
@ -1073,9 +1092,8 @@ static int execute_commands(MYSQL *mysql,int argc, char **argv)
|
|||
}
|
||||
case ADMIN_FLUSH_ALL_STATUS:
|
||||
{
|
||||
if (mysql_query(mysql,
|
||||
"flush status,table_statistics,index_statistics,"
|
||||
"user_statistics,client_statistics"))
|
||||
if (flush(mysql, "status,table_statistics,index_statistics,"
|
||||
"user_statistics,client_statistics"))
|
||||
{
|
||||
my_printf_error(0, "flush failed; error: '%s'", error_flags,
|
||||
mysql_error(mysql));
|
||||
|
@ -1093,6 +1111,8 @@ static int execute_commands(MYSQL *mysql,int argc, char **argv)
|
|||
start_time=time((time_t*) 0);
|
||||
my_rnd_init(&rand_st,(ulong) start_time,(ulong) start_time/2);
|
||||
|
||||
if (maybe_disable_binlog(mysql))
|
||||
return -1;
|
||||
if (argc < 1)
|
||||
{
|
||||
my_printf_error(0, "Too few arguments to change password", error_flags);
|
||||
|
@ -1106,7 +1126,8 @@ static int execute_commands(MYSQL *mysql,int argc, char **argv)
|
|||
if (strcmp(typed_password, verified) != 0)
|
||||
{
|
||||
my_printf_error(0,"Passwords don't match",MYF(ME_BELL));
|
||||
return -1;
|
||||
ret = -1;
|
||||
goto password_done;
|
||||
}
|
||||
}
|
||||
else
|
||||
|
@ -1133,7 +1154,8 @@ static int execute_commands(MYSQL *mysql,int argc, char **argv)
|
|||
{
|
||||
my_printf_error(0, "Could not determine old_passwords setting from server; error: '%s'",
|
||||
error_flags, mysql_error(mysql));
|
||||
return -1;
|
||||
ret = -1;
|
||||
goto password_done;
|
||||
}
|
||||
else
|
||||
{
|
||||
|
@ -1144,7 +1166,8 @@ static int execute_commands(MYSQL *mysql,int argc, char **argv)
|
|||
"Could not get old_passwords setting from "
|
||||
"server; error: '%s'",
|
||||
error_flags, mysql_error(mysql));
|
||||
return -1;
|
||||
ret = -1;
|
||||
goto password_done;
|
||||
}
|
||||
if (!mysql_num_rows(res))
|
||||
old= 1;
|
||||
|
@ -1169,15 +1192,15 @@ static int execute_commands(MYSQL *mysql,int argc, char **argv)
|
|||
{
|
||||
my_printf_error(0, "Can't turn off logging; error: '%s'",
|
||||
error_flags, mysql_error(mysql));
|
||||
return -1;
|
||||
ret = -1;
|
||||
}
|
||||
else
|
||||
if (mysql_query(mysql,buff))
|
||||
{
|
||||
if (mysql_errno(mysql)!=1290)
|
||||
{
|
||||
my_printf_error(0,"unable to change password; error: '%s'",
|
||||
error_flags, mysql_error(mysql));
|
||||
return -1;
|
||||
}
|
||||
else
|
||||
{
|
||||
|
@ -1191,9 +1214,10 @@ static int execute_commands(MYSQL *mysql,int argc, char **argv)
|
|||
" --skip-grant-tables).\n"
|
||||
"Use: \"mysqladmin flush-privileges password '*'\""
|
||||
" instead", error_flags);
|
||||
return -1;
|
||||
}
|
||||
ret = -1;
|
||||
}
|
||||
password_done:
|
||||
/* free up memory from prompted password */
|
||||
if (typed_password != argv[1])
|
||||
{
|
||||
|
@ -1300,7 +1324,7 @@ static int execute_commands(MYSQL *mysql,int argc, char **argv)
|
|||
return 1;
|
||||
}
|
||||
}
|
||||
return 0;
|
||||
return ret;
|
||||
}
|
||||
|
||||
/**
|
||||
|
|
|
@ -68,6 +68,7 @@ CHARSET_INFO* system_charset_info= &my_charset_utf8_general_ci;
|
|||
|
||||
/* Needed for Flashback */
|
||||
DYNAMIC_ARRAY binlog_events; // Storing the events output string
|
||||
DYNAMIC_ARRAY events_in_stmt; // Storing the events that in one statement
|
||||
String stop_event_string; // Storing the STOP_EVENT output string
|
||||
|
||||
char server_version[SERVER_VERSION_LENGTH];
|
||||
|
@ -894,6 +895,25 @@ static bool print_row_event(PRINT_EVENT_INFO *print_event_info, Log_event *ev,
|
|||
print_event_info->m_table_map_ignored.get_table(table_id);
|
||||
bool skip_event= (ignored_map != NULL);
|
||||
|
||||
if (opt_flashback)
|
||||
{
|
||||
Rows_log_event *e= (Rows_log_event*) ev;
|
||||
// The last Row_log_event will be the first event in Flashback
|
||||
if (is_stmt_end)
|
||||
e->clear_flags(Rows_log_event::STMT_END_F);
|
||||
// The first Row_log_event will be the last event in Flashback
|
||||
if (events_in_stmt.elements == 0)
|
||||
e->set_flags(Rows_log_event::STMT_END_F);
|
||||
// Update the temp_buf
|
||||
e->update_flags();
|
||||
|
||||
if (insert_dynamic(&events_in_stmt, (uchar *) &ev))
|
||||
{
|
||||
error("Out of memory: can't allocate memory to store the flashback events.");
|
||||
exit(1);
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
end of statement check:
|
||||
i) destroy/free ignored maps
|
||||
|
@ -945,7 +965,36 @@ static bool print_row_event(PRINT_EVENT_INFO *print_event_info, Log_event *ev,
|
|||
if (skip_event)
|
||||
return 0;
|
||||
|
||||
return print_base64(print_event_info, ev);
|
||||
if (!opt_flashback)
|
||||
return print_base64(print_event_info, ev);
|
||||
else
|
||||
{
|
||||
if (is_stmt_end)
|
||||
{
|
||||
bool res= false;
|
||||
Log_event *e= NULL;
|
||||
|
||||
// Print the row_event from the last one to the first one
|
||||
for (uint i= events_in_stmt.elements; i > 0; --i)
|
||||
{
|
||||
e= *(dynamic_element(&events_in_stmt, i - 1, Log_event**));
|
||||
res= res || print_base64(print_event_info, e);
|
||||
}
|
||||
// Copy all output into the Log_event
|
||||
ev->output_buf.copy(e->output_buf);
|
||||
// Delete Log_event
|
||||
for (uint i= 0; i < events_in_stmt.elements-1; ++i)
|
||||
{
|
||||
e= *(dynamic_element(&events_in_stmt, i, Log_event**));
|
||||
delete e;
|
||||
}
|
||||
reset_dynamic(&events_in_stmt);
|
||||
|
||||
return res;
|
||||
}
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
|
@ -1386,6 +1435,8 @@ Exit_status process_event(PRINT_EVENT_INFO *print_event_info, Log_event *ev,
|
|||
}
|
||||
if (print_base64(print_event_info, ev))
|
||||
goto err;
|
||||
if (opt_flashback)
|
||||
reset_dynamic(&events_in_stmt);
|
||||
break;
|
||||
}
|
||||
case WRITE_ROWS_EVENT:
|
||||
|
@ -1402,9 +1453,12 @@ Exit_status process_event(PRINT_EVENT_INFO *print_event_info, Log_event *ev,
|
|||
case DELETE_ROWS_COMPRESSED_EVENT_V1:
|
||||
{
|
||||
Rows_log_event *e= (Rows_log_event*) ev;
|
||||
bool is_stmt_end= e->get_flags(Rows_log_event::STMT_END_F);
|
||||
if (print_row_event(print_event_info, ev, e->get_table_id(),
|
||||
e->get_flags(Rows_log_event::STMT_END_F)))
|
||||
goto err;
|
||||
if (!is_stmt_end)
|
||||
destroy_evt= FALSE;
|
||||
break;
|
||||
}
|
||||
case PRE_GA_WRITE_ROWS_EVENT:
|
||||
|
@ -1412,9 +1466,12 @@ Exit_status process_event(PRINT_EVENT_INFO *print_event_info, Log_event *ev,
|
|||
case PRE_GA_UPDATE_ROWS_EVENT:
|
||||
{
|
||||
Old_rows_log_event *e= (Old_rows_log_event*) ev;
|
||||
bool is_stmt_end= e->get_flags(Rows_log_event::STMT_END_F);
|
||||
if (print_row_event(print_event_info, ev, e->get_table_id(),
|
||||
e->get_flags(Old_rows_log_event::STMT_END_F)))
|
||||
goto err;
|
||||
if (!is_stmt_end)
|
||||
destroy_evt= FALSE;
|
||||
break;
|
||||
}
|
||||
case START_ENCRYPTION_EVENT:
|
||||
|
@ -1459,7 +1516,7 @@ end:
|
|||
&my_charset_bin);
|
||||
else
|
||||
{
|
||||
if (push_dynamic(&binlog_events, (uchar *) &tmp_str))
|
||||
if (insert_dynamic(&binlog_events, (uchar *) &tmp_str))
|
||||
{
|
||||
error("Out of memory: can't allocate memory to store the flashback events.");
|
||||
exit(1);
|
||||
|
@ -2480,7 +2537,7 @@ static Exit_status dump_remote_log_entries(PRINT_EVENT_INFO *print_event_info,
|
|||
int2store(buf + BIN_LOG_HEADER_SIZE, binlog_flags);
|
||||
|
||||
size_t tlen = strlen(logname);
|
||||
if (tlen > UINT_MAX)
|
||||
if (tlen > sizeof(buf) - 10)
|
||||
{
|
||||
error("Log name too long.");
|
||||
DBUG_RETURN(ERROR_STOP);
|
||||
|
@ -2915,9 +2972,12 @@ int main(int argc, char** argv)
|
|||
my_set_max_open_files(open_files_limit);
|
||||
|
||||
if (opt_flashback)
|
||||
{
|
||||
my_init_dynamic_array(&binlog_events, sizeof(LEX_STRING), 1024, 1024,
|
||||
MYF(0));
|
||||
|
||||
my_init_dynamic_array(&events_in_stmt, sizeof(Rows_log_event*), 1024, 1024,
|
||||
MYF(0));
|
||||
}
|
||||
if (opt_stop_never)
|
||||
to_last_remote_log= TRUE;
|
||||
|
||||
|
@ -3031,6 +3091,7 @@ int main(int argc, char** argv)
|
|||
}
|
||||
fprintf(result_file, "COMMIT\n/*!*/;\n");
|
||||
delete_dynamic(&binlog_events);
|
||||
delete_dynamic(&events_in_stmt);
|
||||
}
|
||||
|
||||
/* Set delimiter back to semicolon */
|
||||
|
|
|
@ -1,6 +1,6 @@
|
|||
/*
|
||||
Copyright (c) 2001, 2013, Oracle and/or its affiliates.
|
||||
Copyright (c) 2010, 2016, MariaDB
|
||||
Copyright (c) 2010, 2017, MariaDB
|
||||
|
||||
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
|
||||
|
|
|
@ -92,8 +92,7 @@
|
|||
|
||||
static void add_load_option(DYNAMIC_STRING *str, const char *option,
|
||||
const char *option_value);
|
||||
static ulong find_set(TYPELIB *lib, const char *x, size_t length,
|
||||
char **err_pos, uint *err_len);
|
||||
static ulong find_set(TYPELIB *, const char *, size_t, char **, uint *);
|
||||
static char *alloc_query_str(ulong size);
|
||||
|
||||
static void field_escape(DYNAMIC_STRING* in, const char *from);
|
||||
|
@ -114,7 +113,8 @@ static my_bool verbose= 0, opt_no_create_info= 0, opt_no_data= 0, opt_no_data_m
|
|||
opt_slave_apply= 0,
|
||||
opt_include_master_host_port= 0,
|
||||
opt_events= 0, opt_comments_used= 0,
|
||||
opt_alltspcs=0, opt_notspcs= 0, opt_logging;
|
||||
opt_alltspcs=0, opt_notspcs= 0, opt_logging,
|
||||
opt_drop_trigger= 0 ;
|
||||
static my_bool insert_pat_inited= 0, debug_info_flag= 0, debug_check_flag= 0;
|
||||
static ulong opt_max_allowed_packet, opt_net_buffer_length;
|
||||
static MYSQL mysql_connection,*mysql=0;
|
||||
|
@ -233,6 +233,9 @@ static struct my_option my_long_options[] =
|
|||
{"add-drop-table", OPT_DROP, "Add a DROP TABLE before each create.",
|
||||
&opt_drop, &opt_drop, 0, GET_BOOL, NO_ARG, 1, 0, 0, 0, 0,
|
||||
0},
|
||||
{"add-drop-trigger", 0, "Add a DROP TRIGGER before each create.",
|
||||
&opt_drop_trigger, &opt_drop_trigger, 0, GET_BOOL, NO_ARG, 0, 0, 0, 0, 0,
|
||||
0},
|
||||
{"add-locks", OPT_LOCKS, "Add locks around INSERT statements.",
|
||||
&opt_lock, &opt_lock, 0, GET_BOOL, NO_ARG, 1, 0, 0, 0, 0,
|
||||
0},
|
||||
|
@ -2170,6 +2173,7 @@ static void print_xml_comment(FILE *xml_file, size_t len,
|
|||
case '-':
|
||||
if (*(comment_string + 1) == '-') /* Only one hyphen allowed. */
|
||||
break;
|
||||
/* fall through */
|
||||
default:
|
||||
fputc(*comment_string, xml_file);
|
||||
break;
|
||||
|
@ -2207,7 +2211,6 @@ static void print_comment(FILE *sql_file, my_bool is_error, const char *format,
|
|||
print_xml_comment(sql_file, strlen(comment_buff), comment_buff);
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
create_delimiter
|
||||
Generate a new (null-terminated) string that does not exist in query
|
||||
|
@ -2552,7 +2555,7 @@ static uint dump_routines_for_db(char *db)
|
|||
query_buff);
|
||||
print_comment(sql_file, 1,
|
||||
"-- does %s have permissions on mysql.proc?\n\n",
|
||||
current_user);
|
||||
fix_for_comment(current_user));
|
||||
maybe_die(EX_MYSQLERR,"%s has insufficent privileges to %s!",
|
||||
current_user, query_buff);
|
||||
}
|
||||
|
@ -2847,6 +2850,8 @@ static uint get_table_structure(char *table, char *db, char *table_type,
|
|||
|
||||
my_free(scv_buff);
|
||||
|
||||
if (path)
|
||||
my_fclose(sql_file, MYF(MY_WME));
|
||||
DBUG_RETURN(0);
|
||||
}
|
||||
else
|
||||
|
@ -3281,6 +3286,10 @@ static void dump_trigger_old(FILE *sql_file, MYSQL_RES *show_triggers_rs,
|
|||
if (opt_compact)
|
||||
fprintf(sql_file, "/*!50003 SET @OLD_SQL_MODE=@@SQL_MODE*/;\n");
|
||||
|
||||
if (opt_drop_trigger)
|
||||
fprintf(sql_file, "/*!50032 DROP TRIGGER IF EXISTS %s */;\n",
|
||||
(*show_trigger_row)[0]);
|
||||
|
||||
fprintf(sql_file,
|
||||
"DELIMITER ;;\n"
|
||||
"/*!50003 SET SESSION SQL_MODE=\"%s\" */;;\n"
|
||||
|
@ -3361,6 +3370,10 @@ static int dump_trigger(FILE *sql_file, MYSQL_RES *show_create_trigger_rs,
|
|||
|
||||
switch_sql_mode(sql_file, ";", row[1]);
|
||||
|
||||
if (opt_drop_trigger)
|
||||
fprintf(sql_file, "/*!50032 DROP TRIGGER IF EXISTS %s */;\n",
|
||||
row[0]);
|
||||
|
||||
query_str= cover_definer_clause(row[2], strlen(row[2]),
|
||||
C_STRING_WITH_LEN("50017"),
|
||||
C_STRING_WITH_LEN("50003"),
|
||||
|
@ -5471,7 +5484,7 @@ static ulong find_set(TYPELIB *lib, const char *x, size_t length,
|
|||
var_len= (uint) (pos - start);
|
||||
strmake(buff, start, MY_MIN(sizeof(buff) - 1, var_len));
|
||||
find= find_type(buff, lib, FIND_TYPE_BASIC);
|
||||
if (!find)
|
||||
if (find <= 0)
|
||||
{
|
||||
*err_pos= (char*) start;
|
||||
*err_len= var_len;
|
||||
|
@ -5929,8 +5942,7 @@ static my_bool get_view_structure(char *table, char* db)
|
|||
dynstr_free(&ds_view);
|
||||
}
|
||||
|
||||
if (switch_character_set_results(mysql, default_charset))
|
||||
DBUG_RETURN(1);
|
||||
switch_character_set_results(mysql, default_charset);
|
||||
|
||||
/* If a separate .sql file was opened, close it now */
|
||||
if (sql_file != md_result_file)
|
||||
|
|
|
@ -1,6 +1,6 @@
|
|||
/*
|
||||
Copyright (c) 2000, 2015, Oracle and/or its affiliates.
|
||||
Copyright (c) 2011, 2016, MariaDB
|
||||
Copyright (c) 2011, 2017, MariaDB
|
||||
|
||||
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
|
||||
|
@ -677,7 +677,7 @@ int main(int argc, char **argv)
|
|||
MYF(0))))
|
||||
return -2;
|
||||
|
||||
for (counter= 0; *argv != NULL; argv++) /* Loop through tables */
|
||||
for (; *argv != NULL; argv++) /* Loop through tables */
|
||||
{
|
||||
pthread_mutex_lock(&counter_mutex);
|
||||
while (counter == opt_use_threads)
|
||||
|
|
|
@ -1,6 +1,6 @@
|
|||
/*
|
||||
Copyright (c) 2000, 2015, Oracle and/or its affiliates.
|
||||
Copyright (c) 2010, 2016, MariaDB
|
||||
Copyright (c) 2010, 2017, MariaDB
|
||||
|
||||
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
|
||||
|
|
|
@ -1,6 +1,6 @@
|
|||
/*
|
||||
Copyright (c) 2005, 2015, Oracle and/or its affiliates.
|
||||
Copyright (c) 2010, 2016, MariaDB
|
||||
Copyright (c) 2010, 2017, MariaDB
|
||||
|
||||
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
|
||||
|
|
|
@ -1,5 +1,5 @@
|
|||
/* Copyright (c) 2000, 2013, Oracle and/or its affiliates.
|
||||
Copyright (c) 2009, 2016, Monty Program Ab.
|
||||
Copyright (c) 2009, 2017, MariaDB
|
||||
|
||||
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
|
||||
|
@ -82,7 +82,7 @@ static my_bool non_blocking_api_enabled= 0;
|
|||
#define MAX_DELIMITER_LENGTH 16
|
||||
#define DEFAULT_MAX_CONN 64
|
||||
|
||||
#define DIE_BUFF_SIZE 8192
|
||||
#define DIE_BUFF_SIZE 256*1024
|
||||
|
||||
/* Flags controlling send and reap */
|
||||
#define QUERY_SEND_FLAG 1
|
||||
|
@ -574,15 +574,17 @@ struct st_replace *glob_replace= 0;
|
|||
void replace_strings_append(struct st_replace *rep, DYNAMIC_STRING* ds,
|
||||
const char *from, int len);
|
||||
|
||||
static void cleanup_and_exit(int exit_code) __attribute__((noreturn));
|
||||
ATTRIBUTE_NORETURN
|
||||
static void cleanup_and_exit(int exit_code);
|
||||
|
||||
void really_die(const char *msg) __attribute__((noreturn));
|
||||
ATTRIBUTE_NORETURN
|
||||
void really_die(const char *msg);
|
||||
void report_or_die(const char *fmt, ...) ATTRIBUTE_FORMAT(printf, 1, 2);
|
||||
void die(const char *fmt, ...) ATTRIBUTE_FORMAT(printf, 1, 2)
|
||||
__attribute__((noreturn));
|
||||
ATTRIBUTE_NORETURN ATTRIBUTE_FORMAT(printf, 1, 2)
|
||||
void die(const char *fmt, ...);
|
||||
static void make_error_message(char *buf, size_t len, const char *fmt, va_list args);
|
||||
void abort_not_supported_test(const char *fmt, ...) ATTRIBUTE_FORMAT(printf, 1, 2)
|
||||
__attribute__((noreturn));
|
||||
ATTRIBUTE_NORETURN ATTRIBUTE_FORMAT(printf, 1, 2)
|
||||
void abort_not_supported_test(const char *fmt, ...);
|
||||
void verbose_msg(const char *fmt, ...) ATTRIBUTE_FORMAT(printf, 1, 2);
|
||||
void log_msg(const char *fmt, ...) ATTRIBUTE_FORMAT(printf, 1, 2);
|
||||
|
||||
|
@ -602,7 +604,7 @@ void do_eval(DYNAMIC_STRING *query_eval, const char *query,
|
|||
void str_to_file(const char *fname, char *str, int size);
|
||||
void str_to_file2(const char *fname, char *str, int size, my_bool append);
|
||||
|
||||
void fix_win_paths(char *val, int len);
|
||||
void fix_win_paths(char *val, size_t len);
|
||||
const char *get_errname_from_code (uint error_code);
|
||||
int multi_reg_replace(struct st_replace_regex* r,char* val);
|
||||
|
||||
|
@ -1063,7 +1065,7 @@ void do_eval(DYNAMIC_STRING *query_eval, const char *query,
|
|||
if (!(v= var_get(p, &p, 0, 0)))
|
||||
{
|
||||
report_or_die( "Bad variable in eval");
|
||||
return;
|
||||
DBUG_VOID_RETURN;
|
||||
}
|
||||
dynstr_append_mem(query_eval, v->str_val, v->str_val_len);
|
||||
}
|
||||
|
@ -1721,12 +1723,22 @@ int cat_file(DYNAMIC_STRING* ds, const char* filename)
|
|||
{
|
||||
int fd;
|
||||
size_t len;
|
||||
char buff[16384];
|
||||
char *buff;
|
||||
|
||||
if ((fd= my_open(filename, O_RDONLY, MYF(0))) < 0)
|
||||
return 1;
|
||||
while((len= my_read(fd, (uchar*)&buff,
|
||||
sizeof(buff)-1, MYF(0))) > 0)
|
||||
|
||||
len= (size_t) my_seek(fd, 0, SEEK_END, MYF(0));
|
||||
my_seek(fd, 0, SEEK_SET, MYF(0));
|
||||
if (len == (size_t)MY_FILEPOS_ERROR ||
|
||||
!(buff= (char*)my_malloc(len + 1, MYF(0))))
|
||||
{
|
||||
my_close(fd, MYF(0));
|
||||
return 1;
|
||||
}
|
||||
len= my_read(fd, (uchar*)buff, len, MYF(0));
|
||||
my_close(fd, MYF(0));
|
||||
|
||||
{
|
||||
char *p= buff, *start= buff,*end=buff+len;
|
||||
while (p < end)
|
||||
|
@ -1749,7 +1761,7 @@ int cat_file(DYNAMIC_STRING* ds, const char* filename)
|
|||
*p= 0;
|
||||
replace_dynstr_append_mem(ds, start, p-start);
|
||||
}
|
||||
my_close(fd, MYF(0));
|
||||
my_free(buff);
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -1776,7 +1788,7 @@ static int run_command(char* cmd,
|
|||
if (!(res_file= popen(cmd, "r")))
|
||||
{
|
||||
report_or_die("popen(\"%s\", \"r\") failed", cmd);
|
||||
return -1;
|
||||
DBUG_RETURN(-1);
|
||||
}
|
||||
|
||||
while (fgets(buf, sizeof(buf), res_file))
|
||||
|
@ -2642,6 +2654,7 @@ void var_query_set(VAR *var, const char *query, const char** query_end)
|
|||
if (!mysql)
|
||||
{
|
||||
struct st_command command;
|
||||
DBUG_ASSERT(query_end);
|
||||
memset(&command, 0, sizeof(command));
|
||||
command.query= (char*)query;
|
||||
command.first_word_len= (*query_end - query);
|
||||
|
@ -2873,7 +2886,7 @@ void var_set_query_get_value(struct st_command *command, VAR *var)
|
|||
dynstr_free(&ds_query);
|
||||
dynstr_free(&ds_col);
|
||||
eval_expr(var, "", 0);
|
||||
return;
|
||||
DBUG_VOID_RETURN;
|
||||
}
|
||||
|
||||
{
|
||||
|
@ -2898,7 +2911,7 @@ void var_set_query_get_value(struct st_command *command, VAR *var)
|
|||
ds_col.str, ds_query.str);
|
||||
dynstr_free(&ds_query);
|
||||
dynstr_free(&ds_col);
|
||||
return;
|
||||
DBUG_VOID_RETURN;
|
||||
}
|
||||
DBUG_PRINT("info", ("Found column %d with name '%s'",
|
||||
i, fields[i].name));
|
||||
|
@ -3344,7 +3357,7 @@ void do_exec(struct st_command *command)
|
|||
if (!*cmd)
|
||||
{
|
||||
report_or_die("Missing argument in exec");
|
||||
return;
|
||||
DBUG_VOID_RETURN;
|
||||
}
|
||||
command->last_argument= command->end;
|
||||
|
||||
|
@ -3370,6 +3383,12 @@ void do_exec(struct st_command *command)
|
|||
#endif
|
||||
#endif
|
||||
|
||||
if (disable_result_log)
|
||||
{
|
||||
/* Collect stderr output as well, for the case app. crashes or returns error.*/
|
||||
dynstr_append(&ds_cmd, " 2>&1");
|
||||
}
|
||||
|
||||
DBUG_PRINT("info", ("Executing '%s' as '%s'",
|
||||
command->first_argument, ds_cmd.str));
|
||||
|
||||
|
@ -3378,7 +3397,7 @@ void do_exec(struct st_command *command)
|
|||
dynstr_free(&ds_cmd);
|
||||
if (command->abort_on_error)
|
||||
report_or_die("popen(\"%s\", \"r\") failed", command->first_argument);
|
||||
return;
|
||||
DBUG_VOID_RETURN;
|
||||
}
|
||||
|
||||
ds_result= &ds_res;
|
||||
|
@ -3405,16 +3424,7 @@ void do_exec(struct st_command *command)
|
|||
len--;
|
||||
}
|
||||
#endif
|
||||
if (disable_result_log)
|
||||
{
|
||||
if (len)
|
||||
buf[len-1] = 0;
|
||||
DBUG_PRINT("exec_result",("%s", buf));
|
||||
}
|
||||
else
|
||||
{
|
||||
replace_dynstr_append_mem(ds_result, buf, len);
|
||||
}
|
||||
replace_dynstr_append_mem(ds_result, buf, len);
|
||||
}
|
||||
error= pclose(res_file);
|
||||
|
||||
|
@ -3424,7 +3434,7 @@ void do_exec(struct st_command *command)
|
|||
dynstr_free(&ds_sorted);
|
||||
}
|
||||
|
||||
if (error > 0)
|
||||
if (error)
|
||||
{
|
||||
uint status= WEXITSTATUS(error);
|
||||
int i;
|
||||
|
@ -3436,7 +3446,7 @@ void do_exec(struct st_command *command)
|
|||
ds_cmd.str, error, status, errno,
|
||||
ds_res.str);
|
||||
dynstr_free(&ds_cmd);
|
||||
return;
|
||||
DBUG_VOID_RETURN;
|
||||
}
|
||||
|
||||
DBUG_PRINT("info",
|
||||
|
@ -3470,6 +3480,12 @@ void do_exec(struct st_command *command)
|
|||
}
|
||||
|
||||
dynstr_free(&ds_cmd);
|
||||
|
||||
if (disable_result_log)
|
||||
{
|
||||
/* Disable output in case of successful exit.*/
|
||||
dynstr_set(&ds_res,"");
|
||||
}
|
||||
DBUG_VOID_RETURN;
|
||||
}
|
||||
|
||||
|
@ -3569,7 +3585,7 @@ void do_system(struct st_command *command)
|
|||
if (strlen(command->first_argument) == 0)
|
||||
{
|
||||
report_or_die("Missing arguments to system, nothing to do!");
|
||||
return;
|
||||
DBUG_VOID_RETURN;
|
||||
}
|
||||
|
||||
init_dynamic_string(&ds_cmd, 0, command->query_len + 64, 256);
|
||||
|
@ -3607,6 +3623,37 @@ void do_system(struct st_command *command)
|
|||
}
|
||||
|
||||
|
||||
/* returns TRUE if path is inside a sandbox */
|
||||
bool is_sub_path(const char *path, size_t plen, const char *sandbox)
|
||||
{
|
||||
size_t len= strlen(sandbox);
|
||||
if (!sandbox || !len || plen <= len || memcmp(path, sandbox, len - 1)
|
||||
|| path[len] != '/')
|
||||
return false;
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
/* returns TRUE if path cannot be modified */
|
||||
bool bad_path(const char *path)
|
||||
{
|
||||
size_t plen= strlen(path);
|
||||
|
||||
const char *vardir= getenv("MYSQLTEST_VARDIR");
|
||||
if (is_sub_path(path, plen, vardir))
|
||||
return false;
|
||||
|
||||
const char *tmpdir= getenv("MYSQL_TMP_DIR");
|
||||
if (is_sub_path(path, plen, tmpdir))
|
||||
return false;
|
||||
|
||||
report_or_die("Path '%s' is not a subdirectory of MYSQLTEST_VARDIR '%s'"
|
||||
"or MYSQL_TMP_DIR '%s'",
|
||||
path, vardir, tmpdir);
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
SYNOPSIS
|
||||
set_wild_chars
|
||||
|
@ -3665,6 +3712,9 @@ void do_remove_file(struct st_command *command)
|
|||
rm_args, sizeof(rm_args)/sizeof(struct command_arg),
|
||||
' ');
|
||||
|
||||
if (bad_path(ds_filename.str))
|
||||
DBUG_VOID_RETURN;
|
||||
|
||||
DBUG_PRINT("info", ("removing file: %s", ds_filename.str));
|
||||
error= my_delete(ds_filename.str, MYF(disable_warnings ? 0 : MY_WME)) != 0;
|
||||
handle_command_error(command, error, my_errno);
|
||||
|
@ -3708,6 +3758,9 @@ void do_remove_files_wildcard(struct st_command *command)
|
|||
' ');
|
||||
fn_format(dirname, ds_directory.str, "", "", MY_UNPACK_FILENAME);
|
||||
|
||||
if (bad_path(ds_directory.str))
|
||||
DBUG_VOID_RETURN;
|
||||
|
||||
DBUG_PRINT("info", ("listing directory: %s", dirname));
|
||||
if (!(dir_info= my_dir(dirname, MYF(MY_DONT_SORT | MY_WANT_STAT | MY_WME))))
|
||||
{
|
||||
|
@ -3782,6 +3835,9 @@ void do_copy_file(struct st_command *command)
|
|||
sizeof(copy_file_args)/sizeof(struct command_arg),
|
||||
' ');
|
||||
|
||||
if (bad_path(ds_to_file.str))
|
||||
DBUG_VOID_RETURN;
|
||||
|
||||
DBUG_PRINT("info", ("Copy %s to %s", ds_from_file.str, ds_to_file.str));
|
||||
/* MY_HOLD_ORIGINAL_MODES prevents attempts to chown the file */
|
||||
error= (my_copy(ds_from_file.str, ds_to_file.str,
|
||||
|
@ -3819,6 +3875,9 @@ void do_move_file(struct st_command *command)
|
|||
sizeof(move_file_args)/sizeof(struct command_arg),
|
||||
' ');
|
||||
|
||||
if (bad_path(ds_to_file.str))
|
||||
DBUG_VOID_RETURN;
|
||||
|
||||
DBUG_PRINT("info", ("Move %s to %s", ds_from_file.str, ds_to_file.str));
|
||||
error= (my_rename(ds_from_file.str, ds_to_file.str,
|
||||
MYF(disable_warnings ? 0 : MY_WME)) != 0);
|
||||
|
@ -3857,6 +3916,9 @@ void do_chmod_file(struct st_command *command)
|
|||
sizeof(chmod_file_args)/sizeof(struct command_arg),
|
||||
' ');
|
||||
|
||||
if (bad_path(ds_file.str))
|
||||
DBUG_VOID_RETURN;
|
||||
|
||||
/* Parse what mode to set */
|
||||
if (ds_mode.length != 4 ||
|
||||
str2int(ds_mode.str, 8, 0, INT_MAX, &mode) == NullS)
|
||||
|
@ -3928,6 +3990,9 @@ void do_mkdir(struct st_command *command)
|
|||
mkdir_args, sizeof(mkdir_args)/sizeof(struct command_arg),
|
||||
' ');
|
||||
|
||||
if (bad_path(ds_dirname.str))
|
||||
DBUG_VOID_RETURN;
|
||||
|
||||
DBUG_PRINT("info", ("creating directory: %s", ds_dirname.str));
|
||||
error= my_mkdir(ds_dirname.str, 0777, MYF(MY_WME)) != 0;
|
||||
handle_command_error(command, error, my_errno);
|
||||
|
@ -3935,6 +4000,65 @@ void do_mkdir(struct st_command *command)
|
|||
DBUG_VOID_RETURN;
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
Remove directory recursively.
|
||||
*/
|
||||
static int rmtree(const char *dir)
|
||||
{
|
||||
char path[FN_REFLEN];
|
||||
char sep[]={ FN_LIBCHAR, 0 };
|
||||
int err=0;
|
||||
|
||||
MY_DIR *dir_info= my_dir(dir, MYF(MY_DONT_SORT | MY_WANT_STAT));
|
||||
if (!dir_info)
|
||||
return 1;
|
||||
|
||||
for (uint i= 0; i < dir_info->number_of_files; i++)
|
||||
{
|
||||
FILEINFO *file= dir_info->dir_entry + i;
|
||||
/* Skip "." and ".." */
|
||||
if (!strcmp(file->name, ".") || !strcmp(file->name, ".."))
|
||||
continue;
|
||||
|
||||
strxnmov(path, sizeof(path), dir, sep, file->name, NULL);
|
||||
|
||||
if (!MY_S_ISDIR(file->mystat->st_mode))
|
||||
{
|
||||
err= my_delete(path, 0);
|
||||
#ifdef _WIN32
|
||||
/*
|
||||
On Windows, check and possible reset readonly attribute.
|
||||
my_delete(), or DeleteFile does not remove theses files.
|
||||
*/
|
||||
if (err)
|
||||
{
|
||||
DWORD attr= GetFileAttributes(path);
|
||||
if (attr != INVALID_FILE_ATTRIBUTES &&
|
||||
(attr & FILE_ATTRIBUTE_READONLY))
|
||||
{
|
||||
SetFileAttributes(path, attr &~ FILE_ATTRIBUTE_READONLY);
|
||||
err= my_delete(path, 0);
|
||||
}
|
||||
}
|
||||
#endif
|
||||
}
|
||||
else
|
||||
err= rmtree(path);
|
||||
|
||||
if(err)
|
||||
break;
|
||||
}
|
||||
|
||||
my_dirend(dir_info);
|
||||
|
||||
if (!err)
|
||||
err= rmdir(dir);
|
||||
|
||||
return err;
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
SYNOPSIS
|
||||
do_rmdir
|
||||
|
@ -3942,12 +4066,11 @@ void do_mkdir(struct st_command *command)
|
|||
|
||||
DESCRIPTION
|
||||
rmdir <dir_name>
|
||||
Remove the empty directory <dir_name>
|
||||
Remove the directory tree
|
||||
*/
|
||||
|
||||
void do_rmdir(struct st_command *command)
|
||||
{
|
||||
int error;
|
||||
static DYNAMIC_STRING ds_dirname;
|
||||
const struct command_arg rmdir_args[] = {
|
||||
{ "dirname", ARG_STRING, TRUE, &ds_dirname, "Directory to remove" }
|
||||
|
@ -3958,9 +4081,13 @@ void do_rmdir(struct st_command *command)
|
|||
rmdir_args, sizeof(rmdir_args)/sizeof(struct command_arg),
|
||||
' ');
|
||||
|
||||
if (bad_path(ds_dirname.str))
|
||||
DBUG_VOID_RETURN;
|
||||
|
||||
DBUG_PRINT("info", ("removing directory: %s", ds_dirname.str));
|
||||
error= rmdir(ds_dirname.str) != 0;
|
||||
handle_command_error(command, error, errno);
|
||||
if (rmtree(ds_dirname.str))
|
||||
handle_command_error(command, 1, errno);
|
||||
|
||||
dynstr_free(&ds_dirname);
|
||||
DBUG_VOID_RETURN;
|
||||
}
|
||||
|
@ -4073,6 +4200,9 @@ static void do_list_files_write_file_command(struct st_command *command,
|
|||
list_files_args,
|
||||
sizeof(list_files_args)/sizeof(struct command_arg), ' ');
|
||||
|
||||
if (bad_path(ds_filename.str))
|
||||
DBUG_VOID_RETURN;
|
||||
|
||||
init_dynamic_string(&ds_content, "", 1024, 1024);
|
||||
error= get_list_files(&ds_content, &ds_dirname, &ds_wild);
|
||||
handle_command_error(command, error, my_errno);
|
||||
|
@ -4124,7 +4254,8 @@ void read_until_delimiter(DYNAMIC_STRING *ds,
|
|||
while (1)
|
||||
{
|
||||
c= my_getc(cur_file->file);
|
||||
|
||||
if (c == '\r')
|
||||
c= my_getc(cur_file->file);
|
||||
if (c == '\n')
|
||||
{
|
||||
cur_file->lineno++;
|
||||
|
@ -4175,6 +4306,9 @@ void do_write_file_command(struct st_command *command, my_bool append)
|
|||
sizeof(write_file_args)/sizeof(struct command_arg),
|
||||
' ');
|
||||
|
||||
if (bad_path(ds_filename.str))
|
||||
DBUG_VOID_RETURN;
|
||||
|
||||
if (!append && access(ds_filename.str, F_OK) == 0)
|
||||
{
|
||||
/* The file should not be overwritten */
|
||||
|
@ -4556,7 +4690,7 @@ void do_perl(struct st_command *command)
|
|||
if (command->abort_on_error)
|
||||
die("popen(\"%s\", \"r\") failed", buf);
|
||||
dynstr_free(&ds_delimiter);
|
||||
return;
|
||||
DBUG_VOID_RETURN;
|
||||
}
|
||||
|
||||
while (fgets(buf, sizeof(buf), res_file))
|
||||
|
@ -6388,6 +6522,16 @@ my_bool end_of_query(int c)
|
|||
}
|
||||
|
||||
|
||||
static inline bool is_escape_char(char c, char in_string)
|
||||
{
|
||||
if (c != '\\' || in_string == '`') return false;
|
||||
if (!cur_con) return true;
|
||||
uint server_status= cur_con->mysql->server_status;
|
||||
if (server_status & SERVER_STATUS_NO_BACKSLASH_ESCAPES) return false;
|
||||
return !(server_status & SERVER_STATUS_ANSI_QUOTES && in_string == '"');
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
Read one "line" from the file
|
||||
|
||||
|
@ -6414,7 +6558,7 @@ my_bool end_of_query(int c)
|
|||
|
||||
int read_line(char *buf, int size)
|
||||
{
|
||||
char c, UNINIT_VAR(last_quote), last_char= 0;
|
||||
char c, last_quote=0, last_char= 0;
|
||||
char *p= buf, *buf_end= buf + size - 1;
|
||||
int skip_char= 0;
|
||||
my_bool have_slash= FALSE;
|
||||
|
@ -6496,7 +6640,7 @@ int read_line(char *buf, int size)
|
|||
state= R_Q;
|
||||
}
|
||||
}
|
||||
have_slash= (c == '\\');
|
||||
have_slash= is_escape_char(c, last_quote);
|
||||
break;
|
||||
|
||||
case R_COMMENT:
|
||||
|
@ -6566,7 +6710,7 @@ int read_line(char *buf, int size)
|
|||
case R_Q:
|
||||
if (c == last_quote)
|
||||
state= R_NORMAL;
|
||||
else if (c == '\\')
|
||||
else if (is_escape_char(c, last_quote))
|
||||
state= R_SLASH_IN_Q;
|
||||
break;
|
||||
|
||||
|
@ -7345,7 +7489,7 @@ void free_win_path_patterns()
|
|||
=> all \ from c:\mysql\m... until next space is converted into /
|
||||
*/
|
||||
|
||||
void fix_win_paths(char *val, int len)
|
||||
void fix_win_paths(char *val, size_t len)
|
||||
{
|
||||
#ifdef _WIN32
|
||||
uint i;
|
||||
|
@ -9875,25 +10019,39 @@ bool parse_re_part(char *start_re, char *end_re,
|
|||
|
||||
Returns: st_replace_regex struct with pairs of substitutions
|
||||
*/
|
||||
void append_replace_regex(char*, char*, struct st_replace_regex*, char**);
|
||||
|
||||
struct st_replace_regex* init_replace_regex(char* expr)
|
||||
{
|
||||
char *expr_end, *buf_p;
|
||||
struct st_replace_regex* res;
|
||||
char* buf,*expr_end;
|
||||
char* p, start_re, end_re= 1;
|
||||
char* buf_p;
|
||||
uint expr_len= strlen(expr);
|
||||
struct st_regex reg;
|
||||
|
||||
/* my_malloc() will die on fail with MY_FAE */
|
||||
res=(struct st_replace_regex*)my_malloc(
|
||||
sizeof(*res)+expr_len ,MYF(MY_FAE+MY_WME));
|
||||
sizeof(*res)+8192 ,MYF(MY_FAE+MY_WME));
|
||||
my_init_dynamic_array(&res->regex_arr,sizeof(struct st_regex), 128, 128, MYF(0));
|
||||
|
||||
buf= (char*)res + sizeof(*res);
|
||||
expr_end= expr + expr_len;
|
||||
buf_p= (char*)res + sizeof(*res);
|
||||
append_replace_regex(expr, expr_end, res, &buf_p);
|
||||
|
||||
res->odd_buf_len= res->even_buf_len= 8192;
|
||||
res->even_buf= (char*)my_malloc(res->even_buf_len,MYF(MY_WME+MY_FAE));
|
||||
res->odd_buf= (char*)my_malloc(res->odd_buf_len,MYF(MY_WME+MY_FAE));
|
||||
res->buf= res->even_buf;
|
||||
|
||||
return res;
|
||||
}
|
||||
|
||||
|
||||
void append_replace_regex(char* expr, char *expr_end, struct st_replace_regex* res,
|
||||
char **buf_p)
|
||||
{
|
||||
char* p, start_re, end_re= 1;
|
||||
struct st_regex reg;
|
||||
|
||||
p= expr;
|
||||
buf_p= buf;
|
||||
|
||||
/* for each regexp substitution statement */
|
||||
while (p < expr_end)
|
||||
|
@ -9912,13 +10070,34 @@ struct st_replace_regex* init_replace_regex(char* expr)
|
|||
}
|
||||
|
||||
start_re= 0;
|
||||
reg.pattern= buf_p;
|
||||
if (parse_re_part(&start_re, &end_re, &p, expr_end, &buf_p))
|
||||
goto err;
|
||||
reg.pattern= *buf_p;
|
||||
|
||||
reg.replace= buf_p;
|
||||
if (parse_re_part(&start_re, &end_re, &p, expr_end, &buf_p))
|
||||
goto err;
|
||||
/* Allow variable for the *entire* list of replacements */
|
||||
if (*p == '$')
|
||||
{
|
||||
const char *v_end;
|
||||
VAR *val= var_get(p, &v_end, 0, 1);
|
||||
|
||||
if (val)
|
||||
{
|
||||
char *expr, *expr_end;
|
||||
expr= val->str_val;
|
||||
expr_end= expr + val->str_val_len;
|
||||
append_replace_regex(expr, expr_end, res, buf_p);
|
||||
}
|
||||
|
||||
p= (char *) v_end + 1;
|
||||
continue;
|
||||
}
|
||||
else
|
||||
{
|
||||
if (parse_re_part(&start_re, &end_re, &p, expr_end, buf_p))
|
||||
goto err;
|
||||
|
||||
reg.replace= *buf_p;
|
||||
if (parse_re_part(&start_re, &end_re, &p, expr_end, buf_p))
|
||||
goto err;
|
||||
}
|
||||
|
||||
/* Check if we should do matching case insensitive */
|
||||
if (p < expr_end && *p == 'i')
|
||||
|
@ -9931,17 +10110,12 @@ struct st_replace_regex* init_replace_regex(char* expr)
|
|||
if (insert_dynamic(&res->regex_arr, ®))
|
||||
die("Out of memory");
|
||||
}
|
||||
res->odd_buf_len= res->even_buf_len= 8192;
|
||||
res->even_buf= (char*)my_malloc(res->even_buf_len,MYF(MY_WME+MY_FAE));
|
||||
res->odd_buf= (char*)my_malloc(res->odd_buf_len,MYF(MY_WME+MY_FAE));
|
||||
res->buf= res->even_buf;
|
||||
|
||||
return res;
|
||||
return;
|
||||
|
||||
err:
|
||||
my_free(res);
|
||||
die("Error parsing replace_regex \"%s\"", expr);
|
||||
return 0;
|
||||
}
|
||||
|
||||
/*
|
||||
|
@ -10021,12 +10195,6 @@ void do_get_replace_regex(struct st_command *command)
|
|||
{
|
||||
char *expr= command->first_argument;
|
||||
free_replace_regex();
|
||||
/* Allow variable for the *entire* list of replacements */
|
||||
if (*expr == '$')
|
||||
{
|
||||
VAR *val= var_get(expr, NULL, 0, 1);
|
||||
expr= val ? val->str_val : NULL;
|
||||
}
|
||||
if (expr && *expr && !(glob_replace_regex=init_replace_regex(expr)))
|
||||
die("Could not init replace_regex");
|
||||
command->last_argument= command->end;
|
||||
|
|
|
@ -88,20 +88,24 @@ ENDIF()
|
|||
OPTION(ENABLED_LOCAL_INFILE "" ON)
|
||||
SET(WITH_INNODB_SNAPPY OFF CACHE STRING "")
|
||||
IF(WIN32)
|
||||
SET(WITH_LIBARCHIVE STATIC CACHE STRING "")
|
||||
ELSEIF(RPM)
|
||||
SET(WITH_SSL system CACHE STRING "")
|
||||
SET(WITH_ZLIB system CACHE STRING "")
|
||||
SET(CHECKMODULE /usr/bin/checkmodule CACHE STRING "")
|
||||
SET(SEMODULE_PACKAGE /usr/bin/semodule_package CACHE STRING "")
|
||||
SET(WITH_LIBARCHIVE ON CACHE STRING "")
|
||||
ELSEIF(DEB)
|
||||
SET(WITH_SSL system CACHE STRING "")
|
||||
SET(WITH_ZLIB system CACHE STRING "")
|
||||
SET(WITH_LIBWRAP ON)
|
||||
SET(HAVE_EMBEDDED_PRIVILEGE_CONTROL ON)
|
||||
SET(WITH_LIBARCHIVE ON CACHE STRING "")
|
||||
ELSE()
|
||||
SET(WITH_SSL bundled CACHE STRING "")
|
||||
SET(WITH_ZLIB bundled CACHE STRING "")
|
||||
SET(WITH_JEMALLOC static CACHE STRING "")
|
||||
SET(WITH_LIBARCHIVE STATIC CACHE STRING "")
|
||||
ENDIF()
|
||||
|
||||
IF(NOT COMPILATION_COMMENT)
|
||||
|
|
|
@ -23,13 +23,22 @@ SET(CPACK_COMPONENT_SHAREDLIBRARIES_GROUP "shared")
|
|||
SET(CPACK_COMPONENT_COMMON_GROUP "common")
|
||||
SET(CPACK_COMPONENT_CLIENTPLUGINS_GROUP "common")
|
||||
SET(CPACK_COMPONENT_COMPAT_GROUP "compat")
|
||||
SET(CPACK_COMPONENT_BACKUP_GROUP "backup")
|
||||
|
||||
SET(CPACK_COMPONENTS_ALL Server ManPagesServer IniFiles Server_Scripts
|
||||
SupportFiles Development ManPagesDevelopment
|
||||
ManPagesTest Readme ManPagesClient Test
|
||||
Common Client SharedLibraries ClientPlugins)
|
||||
Common Client SharedLibraries ClientPlugins
|
||||
backup
|
||||
)
|
||||
|
||||
SET(CPACK_RPM_PACKAGE_NAME ${CPACK_PACKAGE_NAME})
|
||||
SET(CPACK_PACKAGE_FILE_NAME "${CPACK_RPM_PACKAGE_NAME}-${VERSION}-${RPM}-${CMAKE_SYSTEM_PROCESSOR}")
|
||||
IF(CMAKE_VERSION VERSION_LESS "3.6.0")
|
||||
SET(CPACK_PACKAGE_FILE_NAME "${CPACK_RPM_PACKAGE_NAME}-${VERSION}-${RPM}-${CMAKE_SYSTEM_PROCESSOR}")
|
||||
ELSE()
|
||||
SET(CPACK_RPM_FILE_NAME "RPM-DEFAULT")
|
||||
SET(CPACK_RPM_DEBUGINFO_PACKAGE ON)
|
||||
ENDIF()
|
||||
|
||||
SET(CPACK_RPM_PACKAGE_RELEASE "1%{?dist}")
|
||||
SET(CPACK_RPM_PACKAGE_LICENSE "GPLv2")
|
||||
|
@ -112,6 +121,7 @@ SET(CPACK_RPM_client_USER_FILELIST ${ignored} "%config(noreplace) ${INSTALL_SYSC
|
|||
SET(CPACK_RPM_compat_USER_FILELIST ${ignored})
|
||||
SET(CPACK_RPM_devel_USER_FILELIST ${ignored})
|
||||
SET(CPACK_RPM_test_USER_FILELIST ${ignored})
|
||||
SET(CPACK_RPM_backup_USER_FILELIST ${ignored})
|
||||
|
||||
# "set/append array" - append a set of strings, separated by a space
|
||||
MACRO(SETA var)
|
||||
|
|
|
@ -82,7 +82,3 @@ EXECUTE_PROCESS (
|
|||
IF(NOT RESULT EQUAL 0)
|
||||
MESSAGE(FATAL_ERROR "Could not create initial database \n ${OUT} \n ${ERR}")
|
||||
ENDIF()
|
||||
|
||||
EXECUTE_PROCESS (
|
||||
COMMAND "@CMAKE_COMMAND@" -E touch ${CMAKE_CURRENT_BINARY_DIR}/initdb.dep
|
||||
)
|
||||
|
|
|
@ -45,7 +45,7 @@ MACRO(EXTRACT_LINK_LIBRARIES target var)
|
|||
ENDIF()
|
||||
ENDMACRO()
|
||||
|
||||
EXTRACT_LINK_LIBRARIES(mariadb LIBS)
|
||||
EXTRACT_LINK_LIBRARIES(libmariadb LIBS)
|
||||
EXTRACT_LINK_LIBRARIES(mysqlserver EMB_LIBS)
|
||||
|
||||
SET(LIBS "-lmariadb ${ZLIB_DEPS} ${LIBS} ${openssl_libs}")
|
||||
|
@ -72,6 +72,6 @@ REPLACE_FOR_CLIENTS(CFLAGS "[DU]DBUG_OFF" "[DU]SAFE_MUTEX" "[DU]NDEBUG"
|
|||
"xstrconst" "xc99=none" "AC99" "restrict" "W[-A-Za-z]*=[-A-Za-z0-9]*")
|
||||
|
||||
# Same for --libs
|
||||
REPLACE_FOR_CLIENTS(LIBS lmtmalloc static-libcxa i-static static-intel)
|
||||
REPLACE_FOR_CLIENTS(LIBS "Wl,[^ ]*" lmtmalloc static-libcxa i-static static-intel)
|
||||
REPLACE_FOR_CLIENTS(EMB_LIBS lmtmalloc static-libcxa i-static static-intel)
|
||||
|
||||
|
|
|
@ -1,17 +1,3 @@
|
|||
IF(NOT EXISTS ${CMAKE_SOURCE_DIR}/libmariadb/CMakeLists.txt AND GIT_EXECUTABLE)
|
||||
EXECUTE_PROCESS(COMMAND "${GIT_EXECUTABLE}" submodule init
|
||||
WORKING_DIRECTORY "${CMAKE_SOURCE_DIR}")
|
||||
EXECUTE_PROCESS(COMMAND "${GIT_EXECUTABLE}" submodule update
|
||||
WORKING_DIRECTORY "${CMAKE_SOURCE_DIR}")
|
||||
ENDIF()
|
||||
IF(NOT EXISTS ${CMAKE_SOURCE_DIR}/libmariadb/CMakeLists.txt)
|
||||
MESSAGE(FATAL_ERROR "No MariaDB Connector/C! Run
|
||||
git submodule init
|
||||
git submodule update
|
||||
Then restart the build.
|
||||
")
|
||||
ENDIF()
|
||||
|
||||
SET(OPT CONC_)
|
||||
|
||||
IF (CMAKE_BUILD_TYPE STREQUAL "Debug")
|
||||
|
|
|
@ -139,8 +139,8 @@ IF(MSVC)
|
|||
ENDIF()
|
||||
|
||||
#TODO: update the code and remove the disabled warnings
|
||||
SET(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} /wd4800 /wd4805 /wd4996")
|
||||
SET(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} /wd4800 /wd4805 /wd4996 /wd4291 /wd4577 /we4099")
|
||||
SET(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} /wd4800 /wd4805 /wd4996 /we4700")
|
||||
SET(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} /wd4800 /wd4805 /wd4996 /wd4291 /wd4577 /we4099 /we4700")
|
||||
|
||||
ENDIF()
|
||||
|
||||
|
|
|
@ -5,7 +5,7 @@ MACRO (CHECK_PCRE)
|
|||
IF(WITH_PCRE STREQUAL "system" OR WITH_PCRE STREQUAL "auto")
|
||||
CHECK_LIBRARY_EXISTS(pcre pcre_stack_guard "" HAVE_PCRE)
|
||||
ENDIF()
|
||||
IF(NOT HAVE_PCRE)
|
||||
IF(NOT HAVE_PCRE OR WITH_PCRE STREQUAL "bundled")
|
||||
IF (WITH_PCRE STREQUAL "system")
|
||||
MESSAGE(FATAL_ERROR "system pcre is not found or unusable")
|
||||
ENDIF()
|
||||
|
|
|
@ -201,13 +201,15 @@ MACRO(MYSQL_ADD_PLUGIN)
|
|||
# executable to the linker command line (it would result into link error).
|
||||
# Thus we skip TARGET_LINK_LIBRARIES on Linux, as it would only generate
|
||||
# an additional dependency.
|
||||
IF(NOT ARG_CLIENT)
|
||||
IF(ARG_RECOMPILE_FOR_EMBEDDED OR ARG_STORAGE_ENGINE)
|
||||
IF(MSVC)
|
||||
ADD_DEPENDENCIES(${target} gen_mysqld_lib)
|
||||
TARGET_LINK_LIBRARIES(${target} mysqld_import_lib)
|
||||
ELSEIF(NOT CMAKE_SYSTEM_NAME STREQUAL "Linux")
|
||||
TARGET_LINK_LIBRARIES (${target} mysqld)
|
||||
ENDIF()
|
||||
ELSEIF(CMAKE_SYSTEM_NAME STREQUAL "Linux" AND NOT WITH_ASAN)
|
||||
TARGET_LINK_LIBRARIES (${target} "-Wl,--no-undefined")
|
||||
ENDIF()
|
||||
|
||||
ADD_DEPENDENCIES(${target} GenError ${ARG_DEPENDENCIES})
|
||||
|
@ -233,9 +235,11 @@ MACRO(MYSQL_ADD_PLUGIN)
|
|||
SET(CPACK_RPM_${ARG_COMPONENT}_PACKAGE_PROVIDES "cmake_bug_13248" PARENT_SCOPE)
|
||||
SET(CPACK_RPM_${ARG_COMPONENT}_PACKAGE_OBSOLETES "cmake_bug_13248" PARENT_SCOPE)
|
||||
SET(CPACK_RPM_${ARG_COMPONENT}_USER_FILELIST ${ignored} PARENT_SCOPE)
|
||||
IF(NOT ARG_CLIENT AND NOT ARG_CONFIG AND UNIX)
|
||||
SET(ARG_CONFIG "${CMAKE_CURRENT_BINARY_DIR}/${target}.cnf")
|
||||
FILE(WRITE ${ARG_CONFIG} "[mariadb]\nplugin-load-add=${ARG_MODULE_OUTPUT_NAME}.so\n")
|
||||
IF(NOT ARG_CLIENT AND UNIX)
|
||||
IF (NOT ARG_CONFIG)
|
||||
SET(ARG_CONFIG "${CMAKE_CURRENT_BINARY_DIR}/${target}.cnf")
|
||||
FILE(WRITE ${ARG_CONFIG} "[mariadb]\nplugin-load-add=${ARG_MODULE_OUTPUT_NAME}.so\n")
|
||||
ENDIF()
|
||||
INSTALL(FILES ${ARG_CONFIG} COMPONENT ${ARG_COMPONENT} DESTINATION ${INSTALL_SYSCONF2DIR})
|
||||
SET(CPACK_RPM_${ARG_COMPONENT}_USER_FILELIST ${ignored} "%config(noreplace) ${INSTALL_SYSCONF2DIR}/*" PARENT_SCOPE)
|
||||
ENDIF()
|
||||
|
|
|
@ -1,4 +1,5 @@
|
|||
# Copyright (c) 2009, 2012, Oracle and/or its affiliates. All rights reserved.
|
||||
# Copyright (c) 2009, 2012, Oracle and/or its affiliates.
|
||||
# Copyright (c) 2011, 2017, 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
|
||||
|
@ -11,7 +12,7 @@
|
|||
#
|
||||
# You should have received a copy of the GNU General Public License
|
||||
# along with this program; if not, write to the Free Software
|
||||
# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
|
||||
# We support different versions of SSL:
|
||||
# - "bundled" uses source code in <source dir>/extra/yassl
|
||||
|
@ -159,7 +160,7 @@ MACRO (MYSQL_CHECK_SSL)
|
|||
HAVE_EncryptAes128Gcm)
|
||||
ELSE()
|
||||
IF(WITH_SSL STREQUAL "system")
|
||||
MESSAGE(SEND_ERROR "Cannot find appropriate system libraries for SSL. Use WITH_SSL=bundled to enable SSL support")
|
||||
MESSAGE(SEND_ERROR "Cannot find appropriate system libraries for SSL. Use WITH_SSL=bundled to enable SSL support")
|
||||
ENDIF()
|
||||
MYSQL_USE_BUNDLED_SSL()
|
||||
ENDIF()
|
||||
|
|
31
cmake/submodules.cmake
Normal file
31
cmake/submodules.cmake
Normal file
|
@ -0,0 +1,31 @@
|
|||
# update submodules automatically
|
||||
IF(GIT_EXECUTABLE AND EXISTS "${CMAKE_SOURCE_DIR}/.git")
|
||||
EXECUTE_PROCESS(COMMAND "${GIT_EXECUTABLE}" config --get cmake.update-submodules
|
||||
WORKING_DIRECTORY "${CMAKE_SOURCE_DIR}"
|
||||
OUTPUT_VARIABLE cmake_update_submodules
|
||||
RESULT_VARIABLE git_config_get_result)
|
||||
IF(git_config_get_result EQUAL 128 OR cmake_update_submodules MATCHES no)
|
||||
SET(update_result 0)
|
||||
ELSEIF (cmake_update_submodules MATCHES force)
|
||||
MESSAGE(STATUS "Updating submodules (forced)")
|
||||
EXECUTE_PROCESS(COMMAND "${GIT_EXECUTABLE}" submodule update --init --force
|
||||
WORKING_DIRECTORY "${CMAKE_SOURCE_DIR}"
|
||||
RESULT_VARIABLE update_result)
|
||||
ELSEIF (cmake_update_submodules MATCHES yes)
|
||||
EXECUTE_PROCESS(COMMAND "${GIT_EXECUTABLE}" submodule update --init
|
||||
WORKING_DIRECTORY "${CMAKE_SOURCE_DIR}"
|
||||
RESULT_VARIABLE update_result)
|
||||
ELSE()
|
||||
MESSAGE(STATUS "Updating submodules")
|
||||
EXECUTE_PROCESS(COMMAND "${GIT_EXECUTABLE}" submodule update --init
|
||||
WORKING_DIRECTORY "${CMAKE_SOURCE_DIR}"
|
||||
RESULT_VARIABLE update_result)
|
||||
ENDIF()
|
||||
ENDIF()
|
||||
|
||||
IF(update_result OR NOT EXISTS ${CMAKE_SOURCE_DIR}/libmariadb/CMakeLists.txt)
|
||||
MESSAGE(FATAL_ERROR "No MariaDB Connector/C! Run
|
||||
git submodule update --init
|
||||
Then restart the build.
|
||||
")
|
||||
ENDIF()
|
|
@ -70,9 +70,11 @@ MACRO(CHECK_SYSTEMD)
|
|||
UNSET(HAVE_SYSTEMD_SD_NOTIFYF)
|
||||
MESSAGE_ONCE(systemd "Systemd features not enabled")
|
||||
IF(WITH_SYSTEMD STREQUAL "yes")
|
||||
MESSAGE(FATAL_ERROR "Requested WITH_SYSTEMD=YES however no dependencies installed/found")
|
||||
MESSAGE(FATAL_ERROR "Requested WITH_SYSTEMD=yes however no dependencies installed/found")
|
||||
ENDIF()
|
||||
ENDIF()
|
||||
ELSEIF(NOT WITH_SYSTEMD STREQUAL "no")
|
||||
MESSAGE(FATAL_ERROR "Invalid value for WITH_SYSTEMD. Must be 'yes', 'no', or 'auto'.")
|
||||
ENDIF()
|
||||
ENDIF()
|
||||
ENDMACRO()
|
||||
|
|
|
@ -26,7 +26,7 @@ ENDIF()
|
|||
OPTION(WITH_WSREP "WSREP replication API (to use, e.g. Galera Replication library)" ${with_wsrep_default})
|
||||
|
||||
# Set the patch version
|
||||
SET(WSREP_PATCH_VERSION "19")
|
||||
SET(WSREP_PATCH_VERSION "20")
|
||||
|
||||
# Obtain wsrep API version
|
||||
FILE(STRINGS "${MySQL_SOURCE_DIR}/wsrep/wsrep_api.h" WSREP_API_VERSION
|
||||
|
@ -41,4 +41,3 @@ SET(WSREP_PROC_INFO ${WITH_WSREP})
|
|||
IF(WITH_WSREP)
|
||||
SET(WSREP_PATCH_VERSION "wsrep_${WSREP_VERSION}")
|
||||
ENDIF()
|
||||
|
||||
|
|
|
@ -576,21 +576,4 @@
|
|||
#define __STDC_FORMAT_MACROS
|
||||
#endif
|
||||
|
||||
/*
|
||||
stat structure (from <sys/stat.h>) is conditionally defined
|
||||
to have different layout and size depending on the defined macros.
|
||||
The correct macro is defined in my_config.h, which means it MUST be
|
||||
included first (or at least before <features.h> - so, practically,
|
||||
before including any system headers).
|
||||
|
||||
Check the include order by looking at __GLIBC__ (defined in <features.h>)
|
||||
|
||||
But we cannot force all third-party clients/connectors to include
|
||||
my_config.h first. So, their crashes are their responsibility,
|
||||
we enable this check only for MariaDB sources (SAFE_MUTEX check).
|
||||
*/
|
||||
#if defined(__GLIBC__) && defined(SAFE_MUTEX)
|
||||
#error <my_config.h> MUST be included first!
|
||||
#endif
|
||||
|
||||
#endif
|
||||
|
|
20
debian/additions/enable_encryption.preset
vendored
Normal file
20
debian/additions/enable_encryption.preset
vendored
Normal file
|
@ -0,0 +1,20 @@
|
|||
#
|
||||
# !include this file into your my.cnf (or any of *.cnf files in /etc/mysql/conf.d)
|
||||
# and it will enable data at rest encryption. This is a simple way to
|
||||
# ensure that everything that can be encrypted will be and your
|
||||
# data will not leak unencrypted.
|
||||
#
|
||||
# DO NOT EDIT THIS FILE! On MariaDB upgrades it might be replaced with a
|
||||
# newer version and your edits will be lost. Instead, add your edits
|
||||
# to the .cnf file after the !include directive.
|
||||
#
|
||||
# NOTE that you also need to install an encryption plugin for the encryption
|
||||
# to work. See https://mariadb.com/kb/en/mariadb/data-at-rest-encryption/#encryption-key-management
|
||||
#
|
||||
[mariadb]
|
||||
aria-encrypt-tables
|
||||
encrypt-binlog
|
||||
encrypt-tmp-disk-tables
|
||||
encrypt-tmp-files
|
||||
loose-innodb-encrypt-log
|
||||
loose-innodb-encrypt-tables
|
5
debian/autobake-deb.sh
vendored
5
debian/autobake-deb.sh
vendored
|
@ -81,6 +81,11 @@ if [[ $GCCVERSION -lt 40800 ]] || [[ $(arch) =~ i[346]86 ]]
|
|||
then
|
||||
sed '/Package: mariadb-plugin-rocksdb/,+7d' -i debian/control
|
||||
fi
|
||||
if [[ $GCCVERSION -lt 40800 ]]
|
||||
then
|
||||
sed '/Package: mariadb-plugin-aws-key-management-10.2/,+13d' -i debian/control
|
||||
fi
|
||||
|
||||
|
||||
# Adjust changelog, add new version
|
||||
echo "Incrementing changelog and starting build scripts"
|
||||
|
|
52
debian/control
vendored
52
debian/control
vendored
|
@ -21,7 +21,7 @@ Build-Depends: bison,
|
|||
libpam0g-dev,
|
||||
libpcre3-dev (>= 2:8.35-3.2~),
|
||||
libreadline-gplv2-dev,
|
||||
libssl-dev,
|
||||
libssl-dev | libssl1.0-dev,
|
||||
libsnappy-dev,
|
||||
libsystemd-dev,
|
||||
libxml2-dev,
|
||||
|
@ -30,6 +30,7 @@ Build-Depends: bison,
|
|||
po-debconf,
|
||||
psmisc,
|
||||
unixodbc-dev,
|
||||
uuid-dev,
|
||||
zlib1g-dev (>= 1:1.1.3-5~)
|
||||
Standards-Version: 3.8.2
|
||||
Homepage: http://mariadb.org/
|
||||
|
@ -47,13 +48,9 @@ Conflicts: mariadb-galera-server-10.0 (<< 10.0.5),
|
|||
mariadb-server-5.2,
|
||||
mariadb-server-5.3,
|
||||
mariadb-server-5.5 (<< 5.5.33)
|
||||
Replaces: libmariadbclient18,
|
||||
libmysqlclient18,
|
||||
libmysqlclient19,
|
||||
Replaces: libmysqlclient19,
|
||||
libmysqlclient20
|
||||
Provides: libmariadbclient18,
|
||||
libmysqlclient18,
|
||||
libmysqlclient19,
|
||||
Provides: libmysqlclient19,
|
||||
libmysqlclient20
|
||||
Description: MariaDB database client library
|
||||
MariaDB is a fast, stable and true multi-user, multi-threaded SQL database
|
||||
|
@ -67,27 +64,29 @@ Package: libmariadbclient18
|
|||
Section: libs
|
||||
Architecture: any
|
||||
Depends: libmariadb3 (= ${binary:Version}), ${misc:Depends}
|
||||
Replaces: libmariadbclient18
|
||||
Provides: libmariadbclient18
|
||||
Description: Virtual package to satisfy external depends
|
||||
MariaDB is a fast, stable and true multi-user, multi-threaded SQL database
|
||||
server. SQL (Structured Query Language) is the most popular database query
|
||||
language in the world. The main goals of MariaDB are speed, robustness and
|
||||
ease of use.
|
||||
.
|
||||
This is an empty package that depends on the libmariadb3
|
||||
package.
|
||||
This package provides compatibility symlinks for libmariadb3
|
||||
|
||||
Package: libmysqlclient18
|
||||
Section: libs
|
||||
Architecture: any
|
||||
Depends: libmariadb3 (= ${binary:Version}), ${misc:Depends}
|
||||
Replaces: libmysqlclient18
|
||||
Provides: libmysqlclient18
|
||||
Description: Virtual package to satisfy external depends
|
||||
MariaDB is a fast, stable and true multi-user, multi-threaded SQL database
|
||||
server. SQL (Structured Query Language) is the most popular database query
|
||||
language in the world. The main goals of MariaDB are speed, robustness and
|
||||
ease of use.
|
||||
.
|
||||
This is an empty package that depends on the libmariadb3
|
||||
package.
|
||||
This package provides compatibility symlinks for libmariadb3
|
||||
|
||||
Package: libmariadb-dev
|
||||
Architecture: any
|
||||
|
@ -173,8 +172,7 @@ Description: MariaDB database common files (e.g. /etc/mysql/conf.d/mariadb.cnf)
|
|||
|
||||
Package: mariadb-client-core-10.2
|
||||
Architecture: any
|
||||
Depends: libmariadb3 (>= ${source:Version}),
|
||||
mariadb-common (>= ${source:Version}),
|
||||
Depends: mariadb-common (>= ${source:Version}),
|
||||
${misc:Depends},
|
||||
${shlibs:Depends}
|
||||
Conflicts: mariadb-client-10.0,
|
||||
|
@ -237,7 +235,6 @@ Description: MariaDB database core client binaries
|
|||
Package: mariadb-client-10.2
|
||||
Architecture: any
|
||||
Depends: debianutils (>=1.6),
|
||||
libmariadb3 (>= ${source:Version}),
|
||||
mariadb-client-core-10.2 (>= ${source:Version}),
|
||||
mariadb-common,
|
||||
${misc:Depends},
|
||||
|
@ -291,8 +288,7 @@ Description: MariaDB database client binaries
|
|||
|
||||
Package: mariadb-server-core-10.2
|
||||
Architecture: any
|
||||
Depends: libmariadb3 (>= ${binary:Version}),
|
||||
mariadb-common (>= ${source:Version}),
|
||||
Depends: mariadb-common (>= ${source:Version}),
|
||||
${misc:Depends},
|
||||
${shlibs:Depends}
|
||||
Conflicts: mariadb-server-core-10.0,
|
||||
|
@ -552,6 +548,16 @@ Breaks: mariadb-gssapi-client-10.1, mariadb-gssapi-client-10.2
|
|||
Replaces: mariadb-gssapi-client-10.1, mariadb-gssapi-client-10.2
|
||||
Description: GSSAPI authentication plugin for MariaDB client
|
||||
|
||||
Package: mariadb-backup-10.2
|
||||
Section: database
|
||||
Architecture: any
|
||||
Breaks: mariadb-backup-10.1
|
||||
Replaces: mariadb-backup-10.1
|
||||
Depends: mariadb-server-10.2,
|
||||
${misc:Depends},
|
||||
${shlibs:Depends}
|
||||
Description: Backup tool for MariaDB server
|
||||
|
||||
Package: mariadb-plugin-cracklib-password-check
|
||||
Architecture: any
|
||||
Depends: libcrack2 (>= 2.9.0),
|
||||
|
@ -562,6 +568,20 @@ Description: CrackLib Password Validation Plugin for MariaDB
|
|||
This password validation plugin uses cracklib to allow only
|
||||
sufficiently secure (as defined by cracklib) user passwords in MariaDB.
|
||||
|
||||
Package: mariadb-plugin-aws-key-management-10.2
|
||||
Section: database
|
||||
Architecture: any
|
||||
Breaks: mariadb-aws-key-management-10.1
|
||||
Replaces: mariadb-aws-key-management-10.1
|
||||
Depends: mariadb-server-10.2,
|
||||
libcurl3,
|
||||
${misc:Depends},
|
||||
${shlibs:Depends}
|
||||
Description: Amazon Web Service Key Management Service Plugin for MariaDB
|
||||
This encryption key management plugin gives an interface to the Amazon Web
|
||||
Services Key Management Service for managing encryption keys used for MariaDB
|
||||
data-at-rest encryption.
|
||||
|
||||
Package: mariadb-test
|
||||
Architecture: any
|
||||
Depends: mariadb-client-10.2 (= ${binary:Version}),
|
||||
|
|
5
debian/libmariadb-dev.install
vendored
5
debian/libmariadb-dev.install
vendored
|
@ -1,7 +1,8 @@
|
|||
usr/bin/mysql_config
|
||||
usr/include/mysql/*.h
|
||||
usr/include/mysql/psi/*.h
|
||||
usr/include/mysql
|
||||
usr/lib/*/libmariadb.so
|
||||
usr/lib/*/libmysqlclient.so
|
||||
usr/lib/*/libmariadbclient.so
|
||||
usr/lib/*/libmariadbclient.a
|
||||
usr/lib/*/libmysqlservices.a
|
||||
usr/share/aclocal/mysql.m4
|
||||
|
|
2
debian/libmariadb-dev.links
vendored
2
debian/libmariadb-dev.links
vendored
|
@ -1,2 +0,0 @@
|
|||
usr/lib/libmysqlclient.so.18 usr/lib/libmysqlclient.so
|
||||
usr/lib/libmysqlclient_r.so.18 usr/lib/libmysqlclient_r.so
|
4
debian/libmariadb3.install
vendored
4
debian/libmariadb3.install
vendored
|
@ -1,5 +1,5 @@
|
|||
usr/lib/*/libmariadbclient.so.*
|
||||
usr/lib/*/libmysqlclient.so.*
|
||||
usr/lib/*/libmysqlclient.so.19
|
||||
usr/lib/*/libmysqlclient.so.20
|
||||
usr/lib/*/libmariadb.so.*
|
||||
usr/lib/mysql/plugin/dialog.so
|
||||
usr/lib/mysql/plugin/mysql_clear_password.so
|
||||
|
|
1
debian/libmariadbclient18.install
vendored
Normal file
1
debian/libmariadbclient18.install
vendored
Normal file
|
@ -0,0 +1 @@
|
|||
usr/lib/*/libmariadbclient.so.18
|
1
debian/libmysqlclient18.install
vendored
Normal file
1
debian/libmysqlclient18.install
vendored
Normal file
|
@ -0,0 +1 @@
|
|||
usr/lib/*/libmysqlclient.so.18
|
2
debian/mariadb-backup-10.2.install
vendored
Normal file
2
debian/mariadb-backup-10.2.install
vendored
Normal file
|
@ -0,0 +1,2 @@
|
|||
usr/bin/mariabackup
|
||||
usr/bin/mbstream
|
2
debian/mariadb-plugin-aws-key-management-10.2.install
vendored
Normal file
2
debian/mariadb-plugin-aws-key-management-10.2.install
vendored
Normal file
|
@ -0,0 +1,2 @@
|
|||
usr/lib/mysql/plugin/aws_key_management.so
|
||||
debian/additions/enable_encryption.preset etc/mysql/conf.d/
|
1
debian/mariadb-server-10.2.install
vendored
1
debian/mariadb-server-10.2.install
vendored
|
@ -38,6 +38,7 @@ usr/bin/wsrep_sst_mysqldump
|
|||
usr/bin/wsrep_sst_rsync
|
||||
usr/bin/wsrep_sst_xtrabackup
|
||||
usr/bin/wsrep_sst_xtrabackup-v2
|
||||
usr/bin/wsrep_sst_mariabackup
|
||||
usr/lib/mysql/plugin/auth_pam.so
|
||||
usr/lib/mysql/plugin/auth_socket.so
|
||||
usr/lib/mysql/plugin/file_key_management.so
|
||||
|
|
1
debian/mariadb-server-core-10.2.install
vendored
1
debian/mariadb-server-core-10.2.install
vendored
|
@ -10,6 +10,7 @@ usr/share/mysql/estonian
|
|||
usr/share/mysql/french
|
||||
usr/share/mysql/german
|
||||
usr/share/mysql/greek
|
||||
usr/share/mysql/hindi
|
||||
usr/share/mysql/hungarian
|
||||
usr/share/mysql/italian
|
||||
usr/share/mysql/japanese
|
||||
|
|
18
debian/patches/50_mysql-test__db_test.dpatch
vendored
18
debian/patches/50_mysql-test__db_test.dpatch
vendored
|
@ -11,14 +11,14 @@
|
|||
--- old/mysql-test/mysql-test-run.pl 2009-06-16 14:24:09.000000000 +0200
|
||||
+++ new/mysql-test/mysql-test-run.pl 2009-07-04 00:03:34.000000000 +0200
|
||||
@@ -3578,6 +3578,11 @@ sub mysql_install_db {
|
||||
mtr_appendfile_to_file("$sql_dir/mysql_system_tables_data.sql",
|
||||
$bootstrap_sql_file);
|
||||
mtr_appendfile_to_file("$sql_dir/mysql_system_tables_data.sql",
|
||||
$bootstrap_sql_file);
|
||||
|
||||
+ mtr_tofile($bootstrap_sql_file, "-- Debian removed the default privileges on the 'test' database\n");
|
||||
+ mtr_tofile($bootstrap_sql_file, "INSERT INTO mysql.db VALUES ('%','test','','Y','Y','Y','Y','Y','Y','N','Y','Y','Y','Y','Y','Y','Y','Y','N','N','Y','Y');\n");
|
||||
+ mtr_tofile($bootstrap_sql_file, "INSERT INTO mysql.db VALUES ('%','test\\_%','','Y','Y','Y','Y','Y','Y','N','Y','Y','Y','Y','Y','Y','Y','Y','N','N','Y','Y');\n");
|
||||
+
|
||||
+ mtr_tofile($bootstrap_sql_file, "-- Debian removed the default privileges on the 'test' database\n");
|
||||
+ mtr_tofile($bootstrap_sql_file, "INSERT INTO mysql.db VALUES ('%','test','','Y','Y','Y','Y','Y','Y','N','Y','Y','Y','Y','Y','Y','Y','Y','N','N','Y','Y');\n");
|
||||
+ mtr_tofile($bootstrap_sql_file, "INSERT INTO mysql.db VALUES ('%','test\\_%','','Y','Y','Y','Y','Y','Y','N','Y','Y','Y','Y','Y','Y','Y','Y','N','N','Y','Y');\n");
|
||||
+
|
||||
# Add test data for timezone - this is just a subset, on a real
|
||||
# system these tables will be populated either by mysql_tzinfo_to_sql
|
||||
# or by downloading the timezone table package from our website
|
||||
+
|
||||
# Add test data for timezone - this is just a subset, on a real
|
||||
# system these tables will be populated either by mysql_tzinfo_to_sql
|
||||
# or by downloading the timezone table package from our website
|
||||
|
|
1
debian/rules
vendored
1
debian/rules
vendored
|
@ -162,6 +162,7 @@ override_dh_auto_install:
|
|||
install -D -m 644 debian/mariadb-server-10.2.py $(TMP)/usr/share/apport/package-hooks/source_mariadb-10.2.py
|
||||
|
||||
# Install libmariadbclient18 compatibility links
|
||||
ln -s /usr/lib/$(DEB_HOST_MULTIARCH)/libmariadb.so.3 $(TMP)/usr/lib/$(DEB_HOST_MULTIARCH)/libmariadbclient.so
|
||||
ln -s /usr/lib/$(DEB_HOST_MULTIARCH)/libmariadb.so.3 $(TMP)/usr/lib/$(DEB_HOST_MULTIARCH)/libmariadbclient.so.18
|
||||
|
||||
# Install libmysqlclientclientXX compatibility links
|
||||
|
|
|
@ -79,7 +79,6 @@ IF(WITH_INNOBASE_STORAGE_ENGINE OR WITH_XTRADB_STORAGE_ENGINE)
|
|||
../storage/innobase/ut/ut0ut.cc
|
||||
../storage/innobase/buf/buf0buf.cc
|
||||
../storage/innobase/page/page0zip.cc
|
||||
../storage/innobase/os/os0file.cc
|
||||
../storage/innobase/fil/fil0crypt.cc
|
||||
)
|
||||
|
||||
|
|
File diff suppressed because it is too large
Load diff
117
extra/mariabackup/CMakeLists.txt
Normal file
117
extra/mariabackup/CMakeLists.txt
Normal file
|
@ -0,0 +1,117 @@
|
|||
# Copyright (c) 2013, 2017 Percona LLC and/or its affiliates.
|
||||
#
|
||||
# This program is free software; you can redistribute it and/or modify
|
||||
# it under the terms of the GNU General Public License as published by
|
||||
# the Free Software Foundation; version 2 of the License.
|
||||
#
|
||||
# This program is distributed in the hope that it will be useful,
|
||||
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
# GNU General Public License for more details.
|
||||
#
|
||||
# You should have received a copy of the GNU General Public License
|
||||
# along with this program; if not, write to the Free Software
|
||||
# Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
|
||||
|
||||
|
||||
OPTION(WITH_MARIABACKUP "Include mariabackup" ON)
|
||||
IF(NOT WITH_MARIABACKUP)
|
||||
RETURN()
|
||||
ENDIF()
|
||||
|
||||
|
||||
IF(NOT WIN32)
|
||||
CHECK_SYMBOL_EXISTS(regcomp regex.h HAVE_SYSTEM_REGEX)
|
||||
IF(HAVE_SYSTEM_REGEX)
|
||||
ADD_DEFINITIONS(-DHAVE_SYSTEM_REGEX)
|
||||
ENDIF()
|
||||
ENDIF()
|
||||
|
||||
|
||||
INCLUDE_DIRECTORIES(
|
||||
${CMAKE_SOURCE_DIR}/include
|
||||
${CMAKE_SOURCE_DIR}/sql
|
||||
${CMAKE_CURRENT_SOURCE_DIR}/quicklz
|
||||
${CMAKE_CURRENT_SOURCE_DIR}
|
||||
${CMAKE_CURRENT_SOURCE_DIR}/crc
|
||||
)
|
||||
|
||||
IF(NOT HAVE_SYSTEM_REGEX)
|
||||
INCLUDE_DIRECTORIES(${CMAKE_SOURCE_DIR}/pcre)
|
||||
ENDIF()
|
||||
|
||||
ADD_DEFINITIONS(-UMYSQL_SERVER)
|
||||
########################################################################
|
||||
# xtrabackup binary
|
||||
########################################################################
|
||||
|
||||
IF(WIN32)
|
||||
SET(NT_SERVICE_SOURCE ${PROJECT_SOURCE_DIR}/sql/nt_servc.cc)
|
||||
ELSE()
|
||||
SET(NT_SERVICE_SOURCE)
|
||||
ENDIF()
|
||||
|
||||
ADD_DEFINITIONS(-DPCRE_STATIC=1)
|
||||
|
||||
MYSQL_ADD_EXECUTABLE(mariabackup
|
||||
xtrabackup.cc
|
||||
innobackupex.cc
|
||||
changed_page_bitmap.cc
|
||||
datasink.c
|
||||
ds_buffer.c
|
||||
ds_compress.c
|
||||
ds_local.c
|
||||
ds_stdout.c
|
||||
ds_tmpfile.c
|
||||
ds_xbstream.c
|
||||
fil_cur.cc
|
||||
quicklz/quicklz.c
|
||||
read_filt.cc
|
||||
write_filt.cc
|
||||
wsrep.cc
|
||||
xbstream_write.c
|
||||
backup_mysql.cc
|
||||
backup_copy.cc
|
||||
encryption_plugin.cc
|
||||
${PROJECT_SOURCE_DIR}/sql/net_serv.cc
|
||||
${NT_SERVICE_SOURCE}
|
||||
${PROJECT_SOURCE_DIR}/libmysqld/libmysql.c
|
||||
COMPONENT backup
|
||||
)
|
||||
|
||||
|
||||
# Export all symbols on Unix, for better crash callstacks
|
||||
SET_TARGET_PROPERTIES(mariabackup PROPERTIES ENABLE_EXPORTS TRUE)
|
||||
ADD_SUBDIRECTORY(crc)
|
||||
|
||||
|
||||
TARGET_LINK_LIBRARIES(mariabackup sql crc)
|
||||
|
||||
IF(NOT HAVE_SYSTEM_REGEX)
|
||||
TARGET_LINK_LIBRARIES(mariabackup pcreposix)
|
||||
ENDIF()
|
||||
|
||||
|
||||
########################################################################
|
||||
# xbstream binary
|
||||
########################################################################
|
||||
MYSQL_ADD_EXECUTABLE(mbstream
|
||||
ds_buffer.c
|
||||
ds_local.c
|
||||
ds_stdout.c
|
||||
datasink.c
|
||||
xbstream.c
|
||||
xbstream_read.c
|
||||
xbstream_write.c
|
||||
COMPONENT backup
|
||||
)
|
||||
|
||||
|
||||
TARGET_LINK_LIBRARIES(mbstream
|
||||
mysys
|
||||
crc
|
||||
)
|
||||
|
||||
IF(MSVC)
|
||||
SET_TARGET_PROPERTIES(mbstream PROPERTIES LINK_FLAGS setargv.obj)
|
||||
ENDIF()
|
2017
extra/mariabackup/backup_copy.cc
Normal file
2017
extra/mariabackup/backup_copy.cc
Normal file
File diff suppressed because it is too large
Load diff
51
extra/mariabackup/backup_copy.h
Normal file
51
extra/mariabackup/backup_copy.h
Normal file
|
@ -0,0 +1,51 @@
|
|||
|
||||
#ifndef XTRABACKUP_BACKUP_COPY_H
|
||||
#define XTRABACKUP_BACKUP_COPY_H
|
||||
|
||||
#include <my_global.h>
|
||||
#include "datasink.h"
|
||||
|
||||
/* special files */
|
||||
#define XTRABACKUP_SLAVE_INFO "xtrabackup_slave_info"
|
||||
#define XTRABACKUP_GALERA_INFO "xtrabackup_galera_info"
|
||||
#define XTRABACKUP_BINLOG_INFO "xtrabackup_binlog_info"
|
||||
#define XTRABACKUP_INFO "xtrabackup_info"
|
||||
|
||||
extern bool binlog_locked;
|
||||
|
||||
bool
|
||||
backup_file_printf(const char *filename, const char *fmt, ...)
|
||||
ATTRIBUTE_FORMAT(printf, 2, 0);
|
||||
|
||||
/************************************************************************
|
||||
Return true if first and second arguments are the same path. */
|
||||
bool
|
||||
equal_paths(const char *first, const char *second);
|
||||
|
||||
/************************************************************************
|
||||
Copy file for backup/restore.
|
||||
@return true in case of success. */
|
||||
bool
|
||||
copy_file(ds_ctxt_t *datasink,
|
||||
const char *src_file_path,
|
||||
const char *dst_file_path,
|
||||
uint thread_n);
|
||||
|
||||
/** Start --backup */
|
||||
bool backup_start();
|
||||
/** Release resources after backup_start() */
|
||||
void backup_release();
|
||||
/** Finish after backup_start() and backup_release() */
|
||||
bool backup_finish();
|
||||
bool
|
||||
apply_log_finish();
|
||||
bool
|
||||
copy_back();
|
||||
bool
|
||||
decrypt_decompress();
|
||||
bool
|
||||
is_path_separator(char);
|
||||
bool
|
||||
directory_exists(const char *dir, bool create);
|
||||
|
||||
#endif
|
1706
extra/mariabackup/backup_mysql.cc
Normal file
1706
extra/mariabackup/backup_mysql.cc
Normal file
File diff suppressed because it is too large
Load diff
92
extra/mariabackup/backup_mysql.h
Normal file
92
extra/mariabackup/backup_mysql.h
Normal file
|
@ -0,0 +1,92 @@
|
|||
#ifndef XTRABACKUP_BACKUP_MYSQL_H
|
||||
#define XTRABACKUP_BACKUP_MYSQL_H
|
||||
|
||||
#include <mysql.h>
|
||||
|
||||
/* mysql flavor and version */
|
||||
enum mysql_flavor_t { FLAVOR_UNKNOWN, FLAVOR_MYSQL,
|
||||
FLAVOR_PERCONA_SERVER, FLAVOR_MARIADB };
|
||||
extern mysql_flavor_t server_flavor;
|
||||
extern unsigned long mysql_server_version;
|
||||
|
||||
/* server capabilities */
|
||||
extern bool have_changed_page_bitmaps;
|
||||
extern bool have_backup_locks;
|
||||
extern bool have_lock_wait_timeout;
|
||||
extern bool have_galera_enabled;
|
||||
extern bool have_flush_engine_logs;
|
||||
extern bool have_multi_threaded_slave;
|
||||
extern bool have_gtid_slave;
|
||||
|
||||
|
||||
/* History on server */
|
||||
extern time_t history_start_time;
|
||||
extern time_t history_end_time;
|
||||
extern time_t history_lock_time;
|
||||
|
||||
|
||||
extern bool sql_thread_started;
|
||||
extern char *mysql_slave_position;
|
||||
extern char *mysql_binlog_position;
|
||||
extern char *buffer_pool_filename;
|
||||
|
||||
/** connection to mysql server */
|
||||
extern MYSQL *mysql_connection;
|
||||
|
||||
void
|
||||
capture_tool_command(int argc, char **argv);
|
||||
|
||||
bool
|
||||
select_history();
|
||||
|
||||
bool
|
||||
flush_changed_page_bitmaps();
|
||||
|
||||
void
|
||||
backup_cleanup();
|
||||
|
||||
bool
|
||||
get_mysql_vars(MYSQL *connection);
|
||||
|
||||
bool
|
||||
detect_mysql_capabilities_for_backup();
|
||||
|
||||
MYSQL *
|
||||
xb_mysql_connect();
|
||||
|
||||
MYSQL_RES *
|
||||
xb_mysql_query(MYSQL *connection, const char *query, bool use_result,
|
||||
bool die_on_error = true);
|
||||
|
||||
void
|
||||
unlock_all(MYSQL *connection);
|
||||
|
||||
bool
|
||||
write_current_binlog_file(MYSQL *connection);
|
||||
|
||||
bool
|
||||
write_binlog_info(MYSQL *connection);
|
||||
|
||||
bool
|
||||
write_xtrabackup_info(MYSQL *connection);
|
||||
|
||||
bool
|
||||
write_backup_config_file();
|
||||
|
||||
bool
|
||||
lock_binlog_maybe(MYSQL *connection);
|
||||
|
||||
bool
|
||||
lock_tables(MYSQL *connection);
|
||||
|
||||
bool
|
||||
wait_for_safe_slave(MYSQL *connection);
|
||||
|
||||
bool
|
||||
write_galera_info(MYSQL *connection);
|
||||
|
||||
bool
|
||||
write_slave_info(MYSQL *connection);
|
||||
|
||||
|
||||
#endif
|
32
extra/mariabackup/backup_wsrep.h
Normal file
32
extra/mariabackup/backup_wsrep.h
Normal file
|
@ -0,0 +1,32 @@
|
|||
/******************************************************
|
||||
Percona XtraBackup: hot backup tool for InnoDB
|
||||
(c) 2009-2014 Percona LLC and/or its affiliates
|
||||
Originally Created 3/3/2009 Yasufumi Kinoshita
|
||||
Written by Alexey Kopytov, Aleksandr Kuzminsky, Stewart Smith, Vadim Tkachenko,
|
||||
Yasufumi Kinoshita, Ignacio Nin and Baron Schwartz.
|
||||
|
||||
This program is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; version 2 of the License.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with this program; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
|
||||
*******************************************************/
|
||||
|
||||
#ifndef BACKUP_WSREP_H
|
||||
#define BACKUP_WSREP_H
|
||||
|
||||
/***********************************************************************
|
||||
Store Galera checkpoint info in the 'xtrabackup_galera_info' file, if that
|
||||
information is present in the trx system header. Otherwise, do nothing. */
|
||||
void
|
||||
xb_write_galera_info(bool incremental_prepare);
|
||||
/*==================*/
|
||||
|
||||
#endif
|
1045
extra/mariabackup/changed_page_bitmap.cc
Normal file
1045
extra/mariabackup/changed_page_bitmap.cc
Normal file
File diff suppressed because it is too large
Load diff
85
extra/mariabackup/changed_page_bitmap.h
Normal file
85
extra/mariabackup/changed_page_bitmap.h
Normal file
|
@ -0,0 +1,85 @@
|
|||
/******************************************************
|
||||
XtraBackup: hot backup tool for InnoDB
|
||||
(c) 2009-2012 Percona Inc.
|
||||
Originally Created 3/3/2009 Yasufumi Kinoshita
|
||||
Written by Alexey Kopytov, Aleksandr Kuzminsky, Stewart Smith, Vadim Tkachenko,
|
||||
Yasufumi Kinoshita, Ignacio Nin and Baron Schwartz.
|
||||
|
||||
This program is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; version 2 of the License.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with this program; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
|
||||
|
||||
*******************************************************/
|
||||
|
||||
/* Changed page bitmap interface */
|
||||
|
||||
#ifndef XB_CHANGED_PAGE_BITMAP_H
|
||||
#define XB_CHANGED_PAGE_BITMAP_H
|
||||
|
||||
#include <ut0rbt.h>
|
||||
#include <fil0fil.h>
|
||||
|
||||
/* The changed page bitmap structure */
|
||||
typedef ib_rbt_t xb_page_bitmap;
|
||||
|
||||
struct xb_page_bitmap_range_struct;
|
||||
|
||||
/* The bitmap range iterator over one space id */
|
||||
typedef struct xb_page_bitmap_range_struct xb_page_bitmap_range;
|
||||
|
||||
/****************************************************************//**
|
||||
Read the disk bitmap and build the changed page bitmap tree for the
|
||||
LSN interval incremental_lsn to checkpoint_lsn_start.
|
||||
|
||||
@return the built bitmap tree */
|
||||
xb_page_bitmap*
|
||||
xb_page_bitmap_init(void);
|
||||
/*=====================*/
|
||||
|
||||
/****************************************************************//**
|
||||
Free the bitmap tree. */
|
||||
void
|
||||
xb_page_bitmap_deinit(
|
||||
/*==================*/
|
||||
xb_page_bitmap* bitmap); /*!<in/out: bitmap tree */
|
||||
|
||||
|
||||
/****************************************************************//**
|
||||
Set up a new bitmap range iterator over a given space id changed
|
||||
pages in a given bitmap.
|
||||
|
||||
@return bitmap range iterator */
|
||||
xb_page_bitmap_range*
|
||||
xb_page_bitmap_range_init(
|
||||
/*======================*/
|
||||
xb_page_bitmap* bitmap, /*!< in: bitmap to iterate over */
|
||||
ulint space_id); /*!< in: space id */
|
||||
|
||||
/****************************************************************//**
|
||||
Get the next page id that has its bit set or cleared, i.e. equal to
|
||||
bit_value.
|
||||
|
||||
@return page id */
|
||||
ulint
|
||||
xb_page_bitmap_range_get_next_bit(
|
||||
/*==============================*/
|
||||
xb_page_bitmap_range* bitmap_range, /*!< in/out: bitmap range */
|
||||
ibool bit_value); /*!< in: bit value */
|
||||
|
||||
/****************************************************************//**
|
||||
Free the bitmap range iterator. */
|
||||
void
|
||||
xb_page_bitmap_range_deinit(
|
||||
/*========================*/
|
||||
xb_page_bitmap_range* bitmap_range); /*! in/out: bitmap range */
|
||||
|
||||
#endif
|
174
extra/mariabackup/common.h
Normal file
174
extra/mariabackup/common.h
Normal file
|
@ -0,0 +1,174 @@
|
|||
/******************************************************
|
||||
Copyright (c) 2011-2013 Percona LLC and/or its affiliates.
|
||||
|
||||
Common declarations for XtraBackup.
|
||||
|
||||
This program is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; version 2 of the License.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with this program; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
|
||||
|
||||
*******************************************************/
|
||||
|
||||
#ifndef XB_COMMON_H
|
||||
#define XB_COMMON_H
|
||||
|
||||
#include <my_global.h>
|
||||
#include <mysql_version.h>
|
||||
#include <fcntl.h>
|
||||
#include <stdarg.h>
|
||||
|
||||
|
||||
# define fil_is_user_tablespace_id(i) ((i) > srv_undo_tablespaces_open)
|
||||
|
||||
#ifdef _MSC_VER
|
||||
#define stat _stati64
|
||||
#define PATH_MAX MAX_PATH
|
||||
#endif
|
||||
|
||||
#ifndef HAVE_VASPRINTF
|
||||
static inline int vasprintf(char **strp, const char *fmt, va_list args)
|
||||
{
|
||||
int len;
|
||||
#ifdef _MSC_VER
|
||||
len = _vscprintf(fmt, args);
|
||||
#else
|
||||
len = vsnprintf(NULL, 0, fmt, args);
|
||||
#endif
|
||||
if (len < 0)
|
||||
{
|
||||
return -1;
|
||||
}
|
||||
*strp = (char *)malloc(len + 1);
|
||||
if (!*strp)
|
||||
{
|
||||
return -1;
|
||||
}
|
||||
vsprintf(*strp, fmt, args);
|
||||
return len;
|
||||
}
|
||||
|
||||
static inline int asprintf(char **strp, const char *fmt,...)
|
||||
{
|
||||
va_list args;
|
||||
va_start(args, fmt);
|
||||
int len = vasprintf(strp, fmt, args);
|
||||
va_end(args);
|
||||
return len;
|
||||
}
|
||||
#endif
|
||||
|
||||
#define xb_a(expr) \
|
||||
do { \
|
||||
if (!(expr)) { \
|
||||
msg("Assertion \"%s\" failed at %s:%lu\n", \
|
||||
#expr, __FILE__, (ulong) __LINE__); \
|
||||
abort(); \
|
||||
} \
|
||||
} while (0);
|
||||
|
||||
#ifdef XB_DEBUG
|
||||
#define xb_ad(expr) xb_a(expr)
|
||||
#else
|
||||
#define xb_ad(expr)
|
||||
#endif
|
||||
|
||||
#define XB_DELTA_INFO_SUFFIX ".meta"
|
||||
|
||||
static inline int msg(const char *fmt, ...) ATTRIBUTE_FORMAT(printf, 1, 2);
|
||||
static inline int msg(const char *fmt, ...)
|
||||
{
|
||||
int result;
|
||||
va_list args;
|
||||
|
||||
va_start(args, fmt);
|
||||
result = vfprintf(stderr, fmt, args);
|
||||
va_end(args);
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
static inline int msg_ts(const char *fmt, ...) ATTRIBUTE_FORMAT(printf, 1, 2);
|
||||
static inline int msg_ts(const char *fmt, ...)
|
||||
{
|
||||
int result;
|
||||
time_t t = time(NULL);
|
||||
char date[100];
|
||||
char *line;
|
||||
va_list args;
|
||||
|
||||
strftime(date, sizeof(date), "%y%m%d %H:%M:%S", localtime(&t));
|
||||
|
||||
va_start(args, fmt);
|
||||
result = vasprintf(&line, fmt, args);
|
||||
va_end(args);
|
||||
|
||||
if (result != -1) {
|
||||
result = fprintf(stderr, "%s %s", date, line);
|
||||
free(line);
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
/* Use POSIX_FADV_NORMAL when available */
|
||||
|
||||
#ifdef POSIX_FADV_NORMAL
|
||||
# define USE_POSIX_FADVISE
|
||||
#else
|
||||
# define POSIX_FADV_NORMAL
|
||||
# define POSIX_FADV_SEQUENTIAL
|
||||
# define POSIX_FADV_DONTNEED
|
||||
# define posix_fadvise(a,b,c,d) do {} while(0)
|
||||
#endif
|
||||
|
||||
/***********************************************************************
|
||||
Computes bit shift for a given value. If the argument is not a power
|
||||
of 2, returns 0.*/
|
||||
static inline size_t
|
||||
get_bit_shift(size_t value)
|
||||
{
|
||||
size_t shift;
|
||||
|
||||
if (value == 0)
|
||||
return 0;
|
||||
|
||||
for (shift = 0; !(value & 1); shift++) {
|
||||
value >>= 1;
|
||||
}
|
||||
return (value >> 1) ? 0 : shift;
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
Read 'len' bytes from 'fd'. It is identical to my_read(..., MYF(MY_FULL_IO)),
|
||||
i.e. tries to combine partial reads into a single block of size 'len', except
|
||||
that it bails out on EOF or error, and returns the number of successfully read
|
||||
bytes instead. */
|
||||
static inline size_t
|
||||
xb_read_full(File fd, uchar *buf, size_t len)
|
||||
{
|
||||
size_t tlen = 0;
|
||||
size_t tbytes;
|
||||
|
||||
while (tlen < len) {
|
||||
tbytes = my_read(fd, buf, len - tlen, MYF(MY_WME));
|
||||
if (tbytes == 0 || tbytes == MY_FILE_ERROR) {
|
||||
break;
|
||||
}
|
||||
|
||||
buf += tbytes;
|
||||
tlen += tbytes;
|
||||
}
|
||||
|
||||
return tlen;
|
||||
}
|
||||
|
||||
#endif
|
35
BUILD/compile-pentium-myodbc → extra/mariabackup/crc/CMakeLists.txt
Executable file → Normal file
35
BUILD/compile-pentium-myodbc → extra/mariabackup/crc/CMakeLists.txt
Executable file → Normal file
|
@ -1,28 +1,33 @@
|
|||
#! /bin/sh
|
||||
|
||||
# Copyright (C) 2000 MySQL AB
|
||||
# Use is subject to license terms
|
||||
# Copyright (c) 2017 Percona LLC and/or its affiliates.
|
||||
#
|
||||
# This program is free software; you can redistribute it and/or modify
|
||||
# it under the terms of the GNU General Public License as published by
|
||||
# the Free Software Foundation; version 2 of the License.
|
||||
#
|
||||
|
||||
# This program is distributed in the hope that it will be useful,
|
||||
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
# GNU General Public License for more details.
|
||||
#
|
||||
|
||||
# You should have received a copy of the GNU General Public License
|
||||
# along with this program; if not, write to the Free Software
|
||||
# Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
|
||||
|
||||
path=`dirname $0`
|
||||
. "$path/SETUP.sh"
|
||||
PROJECT(crc C)
|
||||
|
||||
extra_flags="$pentium_cflags $fast_cflags"
|
||||
extra_configs="$pentium_configs --without-server"
|
||||
|
||||
make=no
|
||||
strip=yes
|
||||
|
||||
. "$path/FINISH.sh"
|
||||
IF(NOT CMAKE_CROSSCOMPILING AND NOT MSVC)
|
||||
STRING(TOLOWER ${CMAKE_SYSTEM_PROCESSOR} processor)
|
||||
IF(processor MATCHES "86" OR processor MATCHES "amd64" OR processor MATCHES "x64")
|
||||
# Check for PCLMUL instruction
|
||||
CHECK_C_SOURCE_RUNS("
|
||||
int main()
|
||||
{
|
||||
asm volatile (\"pclmulqdq \\$0x00, %%xmm1, %%xmm0\":::\"cc\");
|
||||
return 0;
|
||||
}" HAVE_CLMUL_INSTRUCTION)
|
||||
ENDIF()
|
||||
ENDIF()
|
||||
IF(HAVE_CLMUL_INSTRUCTION)
|
||||
ADD_DEFINITIONS(-DHAVE_CLMUL_INSTRUCTION)
|
||||
ENDIF()
|
||||
ADD_LIBRARY(crc STATIC crc_glue.c crc-intel-pclmul.c)
|
21
extra/mariabackup/crc/config.h.cmake
Normal file
21
extra/mariabackup/crc/config.h.cmake
Normal file
|
@ -0,0 +1,21 @@
|
|||
/******************************************************
|
||||
Copyright (c) 2017 Percona LLC and/or its affiliates.
|
||||
|
||||
Zlib compatible CRC-32 implementation.
|
||||
|
||||
This program is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; version 2 of the License.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with this program; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
|
||||
|
||||
*******************************************************/
|
||||
|
||||
#cmakedefine HAVE_CLMUL_INSTRUCTION 1
|
511
extra/mariabackup/crc/crc-intel-pclmul.c
Normal file
511
extra/mariabackup/crc/crc-intel-pclmul.c
Normal file
|
@ -0,0 +1,511 @@
|
|||
/******************************************************
|
||||
Copyright (c) 2017 Percona LLC and/or its affiliates.
|
||||
|
||||
CRC32 using Intel's PCLMUL instruction.
|
||||
|
||||
This program is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; version 2 of the License.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with this program; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
|
||||
|
||||
*******************************************************/
|
||||
|
||||
/* crc-intel-pclmul.c - Intel PCLMUL accelerated CRC implementation
|
||||
* Copyright (C) 2016 Jussi Kivilinna <jussi.kivilinna@iki.fi>
|
||||
*
|
||||
* This file is part of Libgcrypt.
|
||||
*
|
||||
* Libgcrypt is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Lesser General Public License as
|
||||
* published by the Free Software Foundation; either version 2.1 of
|
||||
* the License, or (at your option) any later version.
|
||||
*
|
||||
* Libgcrypt is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Lesser General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Lesser General Public
|
||||
* License along with this program; if not, write to the Free Software
|
||||
* Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA
|
||||
*
|
||||
*/
|
||||
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include <stdint.h>
|
||||
|
||||
# define U64_C(c) (c ## UL)
|
||||
|
||||
typedef uint32_t u32;
|
||||
typedef uint16_t u16;
|
||||
typedef uint64_t u64;
|
||||
#ifndef byte
|
||||
typedef uint8_t byte;
|
||||
#endif
|
||||
|
||||
# define _gcry_bswap32 __builtin_bswap32
|
||||
|
||||
#if __GNUC__ >= 4 && defined(__x86_64__) && defined(HAVE_CLMUL_INSTRUCTION)
|
||||
|
||||
#if _GCRY_GCC_VERSION >= 40400 /* 4.4 */
|
||||
/* Prevent compiler from issuing SSE instructions between asm blocks. */
|
||||
# pragma GCC target("no-sse")
|
||||
#endif
|
||||
|
||||
|
||||
#define ALIGNED_16 __attribute__ ((aligned (16)))
|
||||
|
||||
|
||||
struct u16_unaligned_s
|
||||
{
|
||||
u16 a;
|
||||
} __attribute__((packed, aligned (1), may_alias));
|
||||
|
||||
|
||||
/* Constants structure for generic reflected/non-reflected CRC32 CLMUL
|
||||
* functions. */
|
||||
struct crc32_consts_s
|
||||
{
|
||||
/* k: { x^(32*17), x^(32*15), x^(32*5), x^(32*3), x^(32*2), 0 } mod P(x) */
|
||||
u64 k[6];
|
||||
/* my_p: { floor(x^64 / P(x)), P(x) } */
|
||||
u64 my_p[2];
|
||||
};
|
||||
|
||||
|
||||
/* CLMUL constants for CRC32 and CRC32RFC1510. */
|
||||
static const struct crc32_consts_s crc32_consts ALIGNED_16 =
|
||||
{
|
||||
{ /* k[6] = reverse_33bits( x^(32*y) mod P(x) ) */
|
||||
U64_C(0x154442bd4), U64_C(0x1c6e41596), /* y = { 17, 15 } */
|
||||
U64_C(0x1751997d0), U64_C(0x0ccaa009e), /* y = { 5, 3 } */
|
||||
U64_C(0x163cd6124), 0 /* y = 2 */
|
||||
},
|
||||
{ /* my_p[2] = reverse_33bits ( { floor(x^64 / P(x)), P(x) } ) */
|
||||
U64_C(0x1f7011641), U64_C(0x1db710641)
|
||||
}
|
||||
};
|
||||
|
||||
/* Common constants for CRC32 algorithms. */
|
||||
static const byte crc32_refl_shuf_shift[3 * 16] ALIGNED_16 =
|
||||
{
|
||||
0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
|
||||
0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
|
||||
0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07,
|
||||
0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f,
|
||||
0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
|
||||
0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
|
||||
};
|
||||
static const byte crc32_partial_fold_input_mask[16 + 16] ALIGNED_16 =
|
||||
{
|
||||
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||
0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
|
||||
0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
|
||||
};
|
||||
static const u64 crc32_merge9to15_shuf[15 - 9 + 1][2] ALIGNED_16 =
|
||||
{
|
||||
{ U64_C(0x0706050403020100), U64_C(0xffffffffffffff0f) }, /* 9 */
|
||||
{ U64_C(0x0706050403020100), U64_C(0xffffffffffff0f0e) },
|
||||
{ U64_C(0x0706050403020100), U64_C(0xffffffffff0f0e0d) },
|
||||
{ U64_C(0x0706050403020100), U64_C(0xffffffff0f0e0d0c) },
|
||||
{ U64_C(0x0706050403020100), U64_C(0xffffff0f0e0d0c0b) },
|
||||
{ U64_C(0x0706050403020100), U64_C(0xffff0f0e0d0c0b0a) },
|
||||
{ U64_C(0x0706050403020100), U64_C(0xff0f0e0d0c0b0a09) }, /* 15 */
|
||||
};
|
||||
static const u64 crc32_merge5to7_shuf[7 - 5 + 1][2] ALIGNED_16 =
|
||||
{
|
||||
{ U64_C(0xffffff0703020100), U64_C(0xffffffffffffffff) }, /* 5 */
|
||||
{ U64_C(0xffff070603020100), U64_C(0xffffffffffffffff) },
|
||||
{ U64_C(0xff07060503020100), U64_C(0xffffffffffffffff) }, /* 7 */
|
||||
};
|
||||
|
||||
/* PCLMUL functions for reflected CRC32. */
|
||||
static inline void
|
||||
crc32_reflected_bulk (u32 *pcrc, const byte *inbuf, size_t inlen,
|
||||
const struct crc32_consts_s *consts)
|
||||
{
|
||||
if (inlen >= 8 * 16)
|
||||
{
|
||||
asm volatile ("movd %[crc], %%xmm4\n\t"
|
||||
"movdqu %[inbuf_0], %%xmm0\n\t"
|
||||
"movdqu %[inbuf_1], %%xmm1\n\t"
|
||||
"movdqu %[inbuf_2], %%xmm2\n\t"
|
||||
"movdqu %[inbuf_3], %%xmm3\n\t"
|
||||
"pxor %%xmm4, %%xmm0\n\t"
|
||||
:
|
||||
: [inbuf_0] "m" (inbuf[0 * 16]),
|
||||
[inbuf_1] "m" (inbuf[1 * 16]),
|
||||
[inbuf_2] "m" (inbuf[2 * 16]),
|
||||
[inbuf_3] "m" (inbuf[3 * 16]),
|
||||
[crc] "m" (*pcrc)
|
||||
);
|
||||
|
||||
inbuf += 4 * 16;
|
||||
inlen -= 4 * 16;
|
||||
|
||||
asm volatile ("movdqa %[k1k2], %%xmm4\n\t"
|
||||
:
|
||||
: [k1k2] "m" (consts->k[1 - 1])
|
||||
);
|
||||
|
||||
/* Fold by 4. */
|
||||
while (inlen >= 4 * 16)
|
||||
{
|
||||
asm volatile ("movdqu %[inbuf_0], %%xmm5\n\t"
|
||||
"movdqa %%xmm0, %%xmm6\n\t"
|
||||
"pclmulqdq $0x00, %%xmm4, %%xmm0\n\t"
|
||||
"pclmulqdq $0x11, %%xmm4, %%xmm6\n\t"
|
||||
"pxor %%xmm5, %%xmm0\n\t"
|
||||
"pxor %%xmm6, %%xmm0\n\t"
|
||||
|
||||
"movdqu %[inbuf_1], %%xmm5\n\t"
|
||||
"movdqa %%xmm1, %%xmm6\n\t"
|
||||
"pclmulqdq $0x00, %%xmm4, %%xmm1\n\t"
|
||||
"pclmulqdq $0x11, %%xmm4, %%xmm6\n\t"
|
||||
"pxor %%xmm5, %%xmm1\n\t"
|
||||
"pxor %%xmm6, %%xmm1\n\t"
|
||||
|
||||
"movdqu %[inbuf_2], %%xmm5\n\t"
|
||||
"movdqa %%xmm2, %%xmm6\n\t"
|
||||
"pclmulqdq $0x00, %%xmm4, %%xmm2\n\t"
|
||||
"pclmulqdq $0x11, %%xmm4, %%xmm6\n\t"
|
||||
"pxor %%xmm5, %%xmm2\n\t"
|
||||
"pxor %%xmm6, %%xmm2\n\t"
|
||||
|
||||
"movdqu %[inbuf_3], %%xmm5\n\t"
|
||||
"movdqa %%xmm3, %%xmm6\n\t"
|
||||
"pclmulqdq $0x00, %%xmm4, %%xmm3\n\t"
|
||||
"pclmulqdq $0x11, %%xmm4, %%xmm6\n\t"
|
||||
"pxor %%xmm5, %%xmm3\n\t"
|
||||
"pxor %%xmm6, %%xmm3\n\t"
|
||||
:
|
||||
: [inbuf_0] "m" (inbuf[0 * 16]),
|
||||
[inbuf_1] "m" (inbuf[1 * 16]),
|
||||
[inbuf_2] "m" (inbuf[2 * 16]),
|
||||
[inbuf_3] "m" (inbuf[3 * 16])
|
||||
);
|
||||
|
||||
inbuf += 4 * 16;
|
||||
inlen -= 4 * 16;
|
||||
}
|
||||
|
||||
asm volatile ("movdqa %[k3k4], %%xmm6\n\t"
|
||||
"movdqa %[my_p], %%xmm5\n\t"
|
||||
:
|
||||
: [k3k4] "m" (consts->k[3 - 1]),
|
||||
[my_p] "m" (consts->my_p[0])
|
||||
);
|
||||
|
||||
/* Fold 4 to 1. */
|
||||
|
||||
asm volatile ("movdqa %%xmm0, %%xmm4\n\t"
|
||||
"pclmulqdq $0x00, %%xmm6, %%xmm0\n\t"
|
||||
"pclmulqdq $0x11, %%xmm6, %%xmm4\n\t"
|
||||
"pxor %%xmm1, %%xmm0\n\t"
|
||||
"pxor %%xmm4, %%xmm0\n\t"
|
||||
|
||||
"movdqa %%xmm0, %%xmm4\n\t"
|
||||
"pclmulqdq $0x00, %%xmm6, %%xmm0\n\t"
|
||||
"pclmulqdq $0x11, %%xmm6, %%xmm4\n\t"
|
||||
"pxor %%xmm2, %%xmm0\n\t"
|
||||
"pxor %%xmm4, %%xmm0\n\t"
|
||||
|
||||
"movdqa %%xmm0, %%xmm4\n\t"
|
||||
"pclmulqdq $0x00, %%xmm6, %%xmm0\n\t"
|
||||
"pclmulqdq $0x11, %%xmm6, %%xmm4\n\t"
|
||||
"pxor %%xmm3, %%xmm0\n\t"
|
||||
"pxor %%xmm4, %%xmm0\n\t"
|
||||
:
|
||||
:
|
||||
);
|
||||
}
|
||||
else
|
||||
{
|
||||
asm volatile ("movd %[crc], %%xmm1\n\t"
|
||||
"movdqu %[inbuf], %%xmm0\n\t"
|
||||
"movdqa %[k3k4], %%xmm6\n\t"
|
||||
"pxor %%xmm1, %%xmm0\n\t"
|
||||
"movdqa %[my_p], %%xmm5\n\t"
|
||||
:
|
||||
: [inbuf] "m" (*inbuf),
|
||||
[crc] "m" (*pcrc),
|
||||
[k3k4] "m" (consts->k[3 - 1]),
|
||||
[my_p] "m" (consts->my_p[0])
|
||||
);
|
||||
|
||||
inbuf += 16;
|
||||
inlen -= 16;
|
||||
}
|
||||
|
||||
/* Fold by 1. */
|
||||
if (inlen >= 16)
|
||||
{
|
||||
while (inlen >= 16)
|
||||
{
|
||||
/* Load next block to XMM2. Fold XMM0 to XMM0:XMM1. */
|
||||
asm volatile ("movdqu %[inbuf], %%xmm2\n\t"
|
||||
"movdqa %%xmm0, %%xmm1\n\t"
|
||||
"pclmulqdq $0x00, %%xmm6, %%xmm0\n\t"
|
||||
"pclmulqdq $0x11, %%xmm6, %%xmm1\n\t"
|
||||
"pxor %%xmm2, %%xmm0\n\t"
|
||||
"pxor %%xmm1, %%xmm0\n\t"
|
||||
:
|
||||
: [inbuf] "m" (*inbuf)
|
||||
);
|
||||
|
||||
inbuf += 16;
|
||||
inlen -= 16;
|
||||
}
|
||||
}
|
||||
|
||||
/* Partial fold. */
|
||||
if (inlen)
|
||||
{
|
||||
/* Load last input and add padding zeros. */
|
||||
asm volatile ("movdqu %[shr_shuf], %%xmm3\n\t"
|
||||
"movdqu %[shl_shuf], %%xmm4\n\t"
|
||||
"movdqu %[mask], %%xmm2\n\t"
|
||||
|
||||
"movdqa %%xmm0, %%xmm1\n\t"
|
||||
"pshufb %%xmm4, %%xmm0\n\t"
|
||||
"movdqu %[inbuf], %%xmm4\n\t"
|
||||
"pshufb %%xmm3, %%xmm1\n\t"
|
||||
"pand %%xmm4, %%xmm2\n\t"
|
||||
"por %%xmm1, %%xmm2\n\t"
|
||||
|
||||
"movdqa %%xmm0, %%xmm1\n\t"
|
||||
"pclmulqdq $0x00, %%xmm6, %%xmm0\n\t"
|
||||
"pclmulqdq $0x11, %%xmm6, %%xmm1\n\t"
|
||||
"pxor %%xmm2, %%xmm0\n\t"
|
||||
"pxor %%xmm1, %%xmm0\n\t"
|
||||
:
|
||||
: [inbuf] "m" (*(inbuf - 16 + inlen)),
|
||||
[mask] "m" (crc32_partial_fold_input_mask[inlen]),
|
||||
[shl_shuf] "m" (crc32_refl_shuf_shift[inlen]),
|
||||
[shr_shuf] "m" (crc32_refl_shuf_shift[inlen + 16])
|
||||
);
|
||||
|
||||
inbuf += inlen;
|
||||
inlen -= inlen;
|
||||
}
|
||||
|
||||
/* Final fold. */
|
||||
asm volatile (/* reduce 128-bits to 96-bits */
|
||||
"movdqa %%xmm0, %%xmm1\n\t"
|
||||
"pclmulqdq $0x10, %%xmm6, %%xmm0\n\t"
|
||||
"psrldq $8, %%xmm1\n\t"
|
||||
"pxor %%xmm1, %%xmm0\n\t"
|
||||
|
||||
/* reduce 96-bits to 64-bits */
|
||||
"pshufd $0xfc, %%xmm0, %%xmm1\n\t" /* [00][00][00][x] */
|
||||
"pshufd $0xf9, %%xmm0, %%xmm0\n\t" /* [00][00][x>>64][x>>32] */
|
||||
"pclmulqdq $0x00, %[k5], %%xmm1\n\t" /* [00][00][xx][xx] */
|
||||
"pxor %%xmm1, %%xmm0\n\t" /* top 64-bit are zero */
|
||||
|
||||
/* barrett reduction */
|
||||
"pshufd $0xf3, %%xmm0, %%xmm1\n\t" /* [00][00][x>>32][00] */
|
||||
"pslldq $4, %%xmm0\n\t" /* [??][x>>32][??][??] */
|
||||
"pclmulqdq $0x00, %%xmm5, %%xmm1\n\t" /* [00][xx][xx][00] */
|
||||
"pclmulqdq $0x10, %%xmm5, %%xmm1\n\t" /* [00][xx][xx][00] */
|
||||
"pxor %%xmm1, %%xmm0\n\t"
|
||||
|
||||
/* store CRC */
|
||||
"pextrd $2, %%xmm0, %[out]\n\t"
|
||||
: [out] "=m" (*pcrc)
|
||||
: [k5] "m" (consts->k[5 - 1])
|
||||
);
|
||||
}
|
||||
|
||||
static inline void
|
||||
crc32_reflected_less_than_16 (u32 *pcrc, const byte *inbuf, size_t inlen,
|
||||
const struct crc32_consts_s *consts)
|
||||
{
|
||||
if (inlen < 4)
|
||||
{
|
||||
u32 crc = *pcrc;
|
||||
u32 data;
|
||||
|
||||
asm volatile ("movdqa %[my_p], %%xmm5\n\t"
|
||||
:
|
||||
: [my_p] "m" (consts->my_p[0])
|
||||
);
|
||||
|
||||
if (inlen == 1)
|
||||
{
|
||||
data = inbuf[0];
|
||||
data ^= crc;
|
||||
data <<= 24;
|
||||
crc >>= 8;
|
||||
}
|
||||
else if (inlen == 2)
|
||||
{
|
||||
data = ((const struct u16_unaligned_s *)inbuf)->a;
|
||||
data ^= crc;
|
||||
data <<= 16;
|
||||
crc >>= 16;
|
||||
}
|
||||
else
|
||||
{
|
||||
data = ((const struct u16_unaligned_s *)inbuf)->a;
|
||||
data |= inbuf[2] << 16;
|
||||
data ^= crc;
|
||||
data <<= 8;
|
||||
crc >>= 24;
|
||||
}
|
||||
|
||||
/* Barrett reduction */
|
||||
asm volatile ("movd %[in], %%xmm0\n\t"
|
||||
"movd %[crc], %%xmm1\n\t"
|
||||
|
||||
"pclmulqdq $0x00, %%xmm5, %%xmm0\n\t" /* [00][00][xx][xx] */
|
||||
"psllq $32, %%xmm1\n\t"
|
||||
"pshufd $0xfc, %%xmm0, %%xmm0\n\t" /* [00][00][00][x] */
|
||||
"pclmulqdq $0x10, %%xmm5, %%xmm0\n\t" /* [00][00][xx][xx] */
|
||||
"pxor %%xmm1, %%xmm0\n\t"
|
||||
|
||||
"pextrd $1, %%xmm0, %[out]\n\t"
|
||||
: [out] "=m" (*pcrc)
|
||||
: [in] "rm" (data),
|
||||
[crc] "rm" (crc)
|
||||
);
|
||||
}
|
||||
else if (inlen == 4)
|
||||
{
|
||||
/* Barrett reduction */
|
||||
asm volatile ("movd %[crc], %%xmm1\n\t"
|
||||
"movd %[in], %%xmm0\n\t"
|
||||
"movdqa %[my_p], %%xmm5\n\t"
|
||||
"pxor %%xmm1, %%xmm0\n\t"
|
||||
|
||||
"pclmulqdq $0x00, %%xmm5, %%xmm0\n\t" /* [00][00][xx][xx] */
|
||||
"pshufd $0xfc, %%xmm0, %%xmm0\n\t" /* [00][00][00][x] */
|
||||
"pclmulqdq $0x10, %%xmm5, %%xmm0\n\t" /* [00][00][xx][xx] */
|
||||
|
||||
"pextrd $1, %%xmm0, %[out]\n\t"
|
||||
: [out] "=m" (*pcrc)
|
||||
: [in] "m" (*inbuf),
|
||||
[crc] "m" (*pcrc),
|
||||
[my_p] "m" (consts->my_p[0])
|
||||
);
|
||||
}
|
||||
else
|
||||
{
|
||||
asm volatile ("movdqu %[shuf], %%xmm4\n\t"
|
||||
"movd %[crc], %%xmm1\n\t"
|
||||
"movdqa %[my_p], %%xmm5\n\t"
|
||||
"movdqa %[k3k4], %%xmm6\n\t"
|
||||
:
|
||||
: [shuf] "m" (crc32_refl_shuf_shift[inlen]),
|
||||
[crc] "m" (*pcrc),
|
||||
[my_p] "m" (consts->my_p[0]),
|
||||
[k3k4] "m" (consts->k[3 - 1])
|
||||
);
|
||||
|
||||
if (inlen >= 8)
|
||||
{
|
||||
asm volatile ("movq %[inbuf], %%xmm0\n\t"
|
||||
:
|
||||
: [inbuf] "m" (*inbuf)
|
||||
);
|
||||
if (inlen > 8)
|
||||
{
|
||||
asm volatile (/*"pinsrq $1, %[inbuf_tail], %%xmm0\n\t"*/
|
||||
"movq %[inbuf_tail], %%xmm2\n\t"
|
||||
"punpcklqdq %%xmm2, %%xmm0\n\t"
|
||||
"pshufb %[merge_shuf], %%xmm0\n\t"
|
||||
:
|
||||
: [inbuf_tail] "m" (inbuf[inlen - 8]),
|
||||
[merge_shuf] "m"
|
||||
(*crc32_merge9to15_shuf[inlen - 9])
|
||||
);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
asm volatile ("movd %[inbuf], %%xmm0\n\t"
|
||||
"pinsrd $1, %[inbuf_tail], %%xmm0\n\t"
|
||||
"pshufb %[merge_shuf], %%xmm0\n\t"
|
||||
:
|
||||
: [inbuf] "m" (*inbuf),
|
||||
[inbuf_tail] "m" (inbuf[inlen - 4]),
|
||||
[merge_shuf] "m"
|
||||
(*crc32_merge5to7_shuf[inlen - 5])
|
||||
);
|
||||
}
|
||||
|
||||
/* Final fold. */
|
||||
asm volatile ("pxor %%xmm1, %%xmm0\n\t"
|
||||
"pshufb %%xmm4, %%xmm0\n\t"
|
||||
|
||||
/* reduce 128-bits to 96-bits */
|
||||
"movdqa %%xmm0, %%xmm1\n\t"
|
||||
"pclmulqdq $0x10, %%xmm6, %%xmm0\n\t"
|
||||
"psrldq $8, %%xmm1\n\t"
|
||||
"pxor %%xmm1, %%xmm0\n\t" /* top 32-bit are zero */
|
||||
|
||||
/* reduce 96-bits to 64-bits */
|
||||
"pshufd $0xfc, %%xmm0, %%xmm1\n\t" /* [00][00][00][x] */
|
||||
"pshufd $0xf9, %%xmm0, %%xmm0\n\t" /* [00][00][x>>64][x>>32] */
|
||||
"pclmulqdq $0x00, %[k5], %%xmm1\n\t" /* [00][00][xx][xx] */
|
||||
"pxor %%xmm1, %%xmm0\n\t" /* top 64-bit are zero */
|
||||
|
||||
/* barrett reduction */
|
||||
"pshufd $0xf3, %%xmm0, %%xmm1\n\t" /* [00][00][x>>32][00] */
|
||||
"pslldq $4, %%xmm0\n\t" /* [??][x>>32][??][??] */
|
||||
"pclmulqdq $0x00, %%xmm5, %%xmm1\n\t" /* [00][xx][xx][00] */
|
||||
"pclmulqdq $0x10, %%xmm5, %%xmm1\n\t" /* [00][xx][xx][00] */
|
||||
"pxor %%xmm1, %%xmm0\n\t"
|
||||
|
||||
/* store CRC */
|
||||
"pextrd $2, %%xmm0, %[out]\n\t"
|
||||
: [out] "=m" (*pcrc)
|
||||
: [k5] "m" (consts->k[5 - 1])
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
void
|
||||
crc32_intel_pclmul (u32 *pcrc, const byte *inbuf, size_t inlen)
|
||||
{
|
||||
const struct crc32_consts_s *consts = &crc32_consts;
|
||||
#if defined(__x86_64__) && defined(__WIN64__)
|
||||
char win64tmp[2 * 16];
|
||||
|
||||
/* XMM6-XMM7 need to be restored after use. */
|
||||
asm volatile ("movdqu %%xmm6, 0*16(%0)\n\t"
|
||||
"movdqu %%xmm7, 1*16(%0)\n\t"
|
||||
:
|
||||
: "r" (win64tmp)
|
||||
: "memory");
|
||||
#endif
|
||||
|
||||
if (!inlen)
|
||||
return;
|
||||
|
||||
if (inlen >= 16)
|
||||
crc32_reflected_bulk(pcrc, inbuf, inlen, consts);
|
||||
else
|
||||
crc32_reflected_less_than_16(pcrc, inbuf, inlen, consts);
|
||||
|
||||
#if defined(__x86_64__) && defined(__WIN64__)
|
||||
/* Restore used registers. */
|
||||
asm volatile("movdqu 0*16(%0), %%xmm6\n\t"
|
||||
"movdqu 1*16(%0), %%xmm7\n\t"
|
||||
:
|
||||
: "r" (win64tmp)
|
||||
: "memory");
|
||||
#endif
|
||||
}
|
||||
|
||||
#endif
|
25
extra/mariabackup/crc/crc-intel-pclmul.h
Normal file
25
extra/mariabackup/crc/crc-intel-pclmul.h
Normal file
|
@ -0,0 +1,25 @@
|
|||
/******************************************************
|
||||
Copyright (c) 2017 Percona LLC and/or its affiliates.
|
||||
|
||||
CRC32 using Intel's PCLMUL instruction.
|
||||
|
||||
This program is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; version 2 of the License.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with this program; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
|
||||
|
||||
*******************************************************/
|
||||
|
||||
#include <stdint.h>
|
||||
#include <stddef.h>
|
||||
|
||||
void
|
||||
crc32_intel_pclmul(uint32_t *pcrc, const uint8_t *inbuf, size_t inlen);
|
72
extra/mariabackup/crc/crc_glue.c
Normal file
72
extra/mariabackup/crc/crc_glue.c
Normal file
|
@ -0,0 +1,72 @@
|
|||
/******************************************************
|
||||
Copyright (c) 2017 Percona LLC and/or its affiliates.
|
||||
|
||||
Zlib compatible CRC-32 implementation.
|
||||
|
||||
This program is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; version 2 of the License.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with this program; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
|
||||
|
||||
*******************************************************/
|
||||
#include "my_config.h"
|
||||
#include "crc_glue.h"
|
||||
#include "crc-intel-pclmul.h"
|
||||
#include <stdint.h>
|
||||
#include <string.h>
|
||||
#include <zlib.h>
|
||||
|
||||
#if __GNUC__ >= 4 && defined(__x86_64__)
|
||||
static int pclmul_enabled = 0;
|
||||
#endif
|
||||
|
||||
#if defined(__GNUC__) && defined(__x86_64__)
|
||||
static
|
||||
uint32_t
|
||||
cpuid(uint32_t* ecx, uint32_t* edx)
|
||||
{
|
||||
uint32_t level;
|
||||
|
||||
asm("cpuid" : "=a" (level) : "a" (0) : "ebx", "ecx", "edx");
|
||||
|
||||
if (level < 1) {
|
||||
return level;
|
||||
}
|
||||
|
||||
asm("cpuid" : "=c" (*ecx), "=d" (*edx)
|
||||
: "a" (1)
|
||||
: "ebx");
|
||||
|
||||
return level;
|
||||
}
|
||||
#endif
|
||||
|
||||
void crc_init() {
|
||||
#if defined(__GNUC__) && defined(__x86_64__)
|
||||
uint32_t ecx, edx;
|
||||
|
||||
if (cpuid(&ecx, &edx) > 0) {
|
||||
pclmul_enabled = ((ecx >> 19) & 1) && ((ecx >> 1) & 1);
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
unsigned long crc32_iso3309(unsigned long crc, const unsigned char *buf, unsigned int len)
|
||||
{
|
||||
#if __GNUC__ >= 4 && defined(__x86_64__) && defined(HAVE_CLMUL_INSTRUCTION)
|
||||
if (pclmul_enabled) {
|
||||
uint32_t crc_accum = crc ^ 0xffffffffL;
|
||||
crc32_intel_pclmul(&crc_accum, buf, len);
|
||||
return crc_accum ^ 0xffffffffL;
|
||||
}
|
||||
#endif
|
||||
return crc32(crc, buf, len);
|
||||
}
|
31
extra/mariabackup/crc/crc_glue.h
Normal file
31
extra/mariabackup/crc/crc_glue.h
Normal file
|
@ -0,0 +1,31 @@
|
|||
/******************************************************
|
||||
Copyright (c) 2017 Percona LLC and/or its affiliates.
|
||||
|
||||
Zlib compatible CRC-32 implementation.
|
||||
|
||||
This program is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; version 2 of the License.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with this program; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
|
||||
|
||||
*******************************************************/
|
||||
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
void crc_init();
|
||||
unsigned long crc32_iso3309(unsigned long crc, const unsigned char *buf, unsigned int len);
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
137
extra/mariabackup/datasink.c
Normal file
137
extra/mariabackup/datasink.c
Normal file
|
@ -0,0 +1,137 @@
|
|||
/******************************************************
|
||||
Copyright (c) 2011-2013 Percona LLC and/or its affiliates.
|
||||
|
||||
Data sink interface.
|
||||
|
||||
This program is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; version 2 of the License.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with this program; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
|
||||
|
||||
*******************************************************/
|
||||
|
||||
#include <my_base.h>
|
||||
#include "common.h"
|
||||
#include "datasink.h"
|
||||
#include "ds_compress.h"
|
||||
#include "ds_archive.h"
|
||||
#include "ds_xbstream.h"
|
||||
#include "ds_local.h"
|
||||
#include "ds_stdout.h"
|
||||
#include "ds_tmpfile.h"
|
||||
#include "ds_buffer.h"
|
||||
|
||||
/************************************************************************
|
||||
Create a datasink of the specified type */
|
||||
ds_ctxt_t *
|
||||
ds_create(const char *root, ds_type_t type)
|
||||
{
|
||||
datasink_t *ds;
|
||||
ds_ctxt_t *ctxt;
|
||||
|
||||
switch (type) {
|
||||
case DS_TYPE_STDOUT:
|
||||
ds = &datasink_stdout;
|
||||
break;
|
||||
case DS_TYPE_LOCAL:
|
||||
ds = &datasink_local;
|
||||
break;
|
||||
case DS_TYPE_ARCHIVE:
|
||||
#ifdef HAVE_LIBARCHIVE
|
||||
ds = &datasink_archive;
|
||||
#else
|
||||
msg("Error : mariabackup was built without libarchive support");
|
||||
exit(EXIT_FAILURE);
|
||||
#endif
|
||||
break;
|
||||
case DS_TYPE_XBSTREAM:
|
||||
ds = &datasink_xbstream;
|
||||
break;
|
||||
case DS_TYPE_COMPRESS:
|
||||
ds = &datasink_compress;
|
||||
break;
|
||||
case DS_TYPE_ENCRYPT:
|
||||
case DS_TYPE_DECRYPT:
|
||||
msg("Error : mariabackup does not support encrypted backups.");
|
||||
exit(EXIT_FAILURE);
|
||||
break;
|
||||
|
||||
case DS_TYPE_TMPFILE:
|
||||
ds = &datasink_tmpfile;
|
||||
break;
|
||||
case DS_TYPE_BUFFER:
|
||||
ds = &datasink_buffer;
|
||||
break;
|
||||
default:
|
||||
msg("Unknown datasink type: %d\n", type);
|
||||
xb_ad(0);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
ctxt = ds->init(root);
|
||||
if (ctxt != NULL) {
|
||||
ctxt->datasink = ds;
|
||||
} else {
|
||||
msg("Error: failed to initialize datasink.\n");
|
||||
exit(EXIT_FAILURE);
|
||||
}
|
||||
|
||||
return ctxt;
|
||||
}
|
||||
|
||||
/************************************************************************
|
||||
Open a datasink file */
|
||||
ds_file_t *
|
||||
ds_open(ds_ctxt_t *ctxt, const char *path, MY_STAT *stat)
|
||||
{
|
||||
ds_file_t *file;
|
||||
|
||||
file = ctxt->datasink->open(ctxt, path, stat);
|
||||
if (file != NULL) {
|
||||
file->datasink = ctxt->datasink;
|
||||
}
|
||||
|
||||
return file;
|
||||
}
|
||||
|
||||
/************************************************************************
|
||||
Write to a datasink file.
|
||||
@return 0 on success, 1 on error. */
|
||||
int
|
||||
ds_write(ds_file_t *file, const void *buf, size_t len)
|
||||
{
|
||||
return file->datasink->write(file, buf, len);
|
||||
}
|
||||
|
||||
/************************************************************************
|
||||
Close a datasink file.
|
||||
@return 0 on success, 1, on error. */
|
||||
int
|
||||
ds_close(ds_file_t *file)
|
||||
{
|
||||
return file->datasink->close(file);
|
||||
}
|
||||
|
||||
/************************************************************************
|
||||
Destroy a datasink handle */
|
||||
void
|
||||
ds_destroy(ds_ctxt_t *ctxt)
|
||||
{
|
||||
ctxt->datasink->deinit(ctxt);
|
||||
}
|
||||
|
||||
/************************************************************************
|
||||
Set the destination pipe for a datasink (only makes sense for compress and
|
||||
tmpfile). */
|
||||
void ds_set_pipe(ds_ctxt_t *ctxt, ds_ctxt_t *pipe_ctxt)
|
||||
{
|
||||
ctxt->pipe_ctxt = pipe_ctxt;
|
||||
}
|
100
extra/mariabackup/datasink.h
Normal file
100
extra/mariabackup/datasink.h
Normal file
|
@ -0,0 +1,100 @@
|
|||
/******************************************************
|
||||
Copyright (c) 2011-2013 Percona LLC and/or its affiliates.
|
||||
|
||||
Data sink interface.
|
||||
|
||||
This program is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; version 2 of the License.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with this program; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
|
||||
|
||||
*******************************************************/
|
||||
|
||||
#ifndef XB_DATASINK_H
|
||||
#define XB_DATASINK_H
|
||||
|
||||
#include <my_global.h>
|
||||
#include <my_dir.h>
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
extern char *xtrabackup_tmpdir;
|
||||
struct datasink_struct;
|
||||
typedef struct datasink_struct datasink_t;
|
||||
|
||||
typedef struct ds_ctxt {
|
||||
datasink_t *datasink;
|
||||
char *root;
|
||||
void *ptr;
|
||||
struct ds_ctxt *pipe_ctxt;
|
||||
} ds_ctxt_t;
|
||||
|
||||
typedef struct {
|
||||
void *ptr;
|
||||
char *path;
|
||||
datasink_t *datasink;
|
||||
} ds_file_t;
|
||||
|
||||
struct datasink_struct {
|
||||
ds_ctxt_t *(*init)(const char *root);
|
||||
ds_file_t *(*open)(ds_ctxt_t *ctxt, const char *path, MY_STAT *stat);
|
||||
int (*write)(ds_file_t *file, const void *buf, size_t len);
|
||||
int (*close)(ds_file_t *file);
|
||||
void (*deinit)(ds_ctxt_t *ctxt);
|
||||
};
|
||||
|
||||
/* Supported datasink types */
|
||||
typedef enum {
|
||||
DS_TYPE_STDOUT,
|
||||
DS_TYPE_LOCAL,
|
||||
DS_TYPE_ARCHIVE,
|
||||
DS_TYPE_XBSTREAM,
|
||||
DS_TYPE_COMPRESS,
|
||||
DS_TYPE_ENCRYPT,
|
||||
DS_TYPE_DECRYPT,
|
||||
DS_TYPE_TMPFILE,
|
||||
DS_TYPE_BUFFER
|
||||
} ds_type_t;
|
||||
|
||||
/************************************************************************
|
||||
Create a datasink of the specified type */
|
||||
ds_ctxt_t *ds_create(const char *root, ds_type_t type);
|
||||
|
||||
/************************************************************************
|
||||
Open a datasink file */
|
||||
ds_file_t *ds_open(ds_ctxt_t *ctxt, const char *path, MY_STAT *stat);
|
||||
|
||||
/************************************************************************
|
||||
Write to a datasink file.
|
||||
@return 0 on success, 1 on error. */
|
||||
int ds_write(ds_file_t *file, const void *buf, size_t len);
|
||||
|
||||
/************************************************************************
|
||||
Close a datasink file.
|
||||
@return 0 on success, 1, on error. */
|
||||
int ds_close(ds_file_t *file);
|
||||
|
||||
/************************************************************************
|
||||
Destroy a datasink handle */
|
||||
void ds_destroy(ds_ctxt_t *ctxt);
|
||||
|
||||
/************************************************************************
|
||||
Set the destination pipe for a datasink (only makes sense for compress and
|
||||
tmpfile). */
|
||||
void ds_set_pipe(ds_ctxt_t *ctxt, ds_ctxt_t *pipe_ctxt);
|
||||
|
||||
#ifdef __cplusplus
|
||||
} /* extern "C" */
|
||||
#endif
|
||||
|
||||
#endif /* XB_DATASINK_H */
|
280
extra/mariabackup/ds_archive.c
Normal file
280
extra/mariabackup/ds_archive.c
Normal file
|
@ -0,0 +1,280 @@
|
|||
/******************************************************
|
||||
Copyright (c) 2013 Percona LLC and/or its affiliates.
|
||||
|
||||
Streaming implementation for XtraBackup.
|
||||
|
||||
This program is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; version 2 of the License.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with this program; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
|
||||
|
||||
*******************************************************/
|
||||
|
||||
#include <my_base.h>
|
||||
#include <archive.h>
|
||||
#include <archive_entry.h>
|
||||
#include "common.h"
|
||||
#include "datasink.h"
|
||||
|
||||
#if ARCHIVE_VERSION_NUMBER < 3000000
|
||||
#define archive_write_add_filter_none(X) archive_write_set_compression_none(X)
|
||||
#define archive_write_free(X) archive_write_finish(X)
|
||||
#endif
|
||||
|
||||
typedef struct {
|
||||
struct archive *archive;
|
||||
ds_file_t *dest_file;
|
||||
pthread_mutex_t mutex;
|
||||
} ds_archive_ctxt_t;
|
||||
|
||||
typedef struct {
|
||||
struct archive_entry *entry;
|
||||
ds_archive_ctxt_t *archive_ctxt;
|
||||
} ds_archive_file_t;
|
||||
|
||||
|
||||
/***********************************************************************
|
||||
General archive interface */
|
||||
|
||||
static ds_ctxt_t *archive_init(const char *root);
|
||||
static ds_file_t *archive_open(ds_ctxt_t *ctxt, const char *path,
|
||||
MY_STAT *mystat);
|
||||
static int archive_write(ds_file_t *file, const void *buf, size_t len);
|
||||
static int archive_close(ds_file_t *file);
|
||||
static void archive_deinit(ds_ctxt_t *ctxt);
|
||||
|
||||
datasink_t datasink_archive = {
|
||||
&archive_init,
|
||||
&archive_open,
|
||||
&archive_write,
|
||||
&archive_close,
|
||||
&archive_deinit
|
||||
};
|
||||
|
||||
static
|
||||
int
|
||||
my_archive_open_callback(struct archive *a __attribute__((unused)),
|
||||
void *data __attribute__((unused)))
|
||||
{
|
||||
return ARCHIVE_OK;
|
||||
}
|
||||
|
||||
static
|
||||
ssize_t
|
||||
my_archive_write_callback(struct archive *a __attribute__((unused)),
|
||||
void *data, const void *buffer, size_t length)
|
||||
{
|
||||
ds_archive_ctxt_t *archive_ctxt;
|
||||
|
||||
archive_ctxt = (ds_archive_ctxt_t *) data;
|
||||
|
||||
xb_ad(archive_ctxt != NULL);
|
||||
xb_ad(archive_ctxt->dest_file != NULL);
|
||||
|
||||
if (!ds_write(archive_ctxt->dest_file, buffer, length)) {
|
||||
return length;
|
||||
}
|
||||
return -1;
|
||||
}
|
||||
|
||||
static
|
||||
int
|
||||
my_archive_close_callback(struct archive *a __attribute__((unused)),
|
||||
void *data __attribute__((unused)))
|
||||
{
|
||||
return ARCHIVE_OK;
|
||||
}
|
||||
|
||||
static
|
||||
ds_ctxt_t *
|
||||
archive_init(const char *root __attribute__((unused)))
|
||||
{
|
||||
ds_ctxt_t *ctxt;
|
||||
ds_archive_ctxt_t *archive_ctxt;
|
||||
struct archive *a;
|
||||
|
||||
ctxt = my_malloc(sizeof(ds_ctxt_t) + sizeof(ds_archive_ctxt_t),
|
||||
MYF(MY_FAE));
|
||||
archive_ctxt = (ds_archive_ctxt_t *)(ctxt + 1);
|
||||
|
||||
if (pthread_mutex_init(&archive_ctxt->mutex, NULL)) {
|
||||
msg("archive_init: pthread_mutex_init() failed.\n");
|
||||
goto err;
|
||||
}
|
||||
|
||||
a = archive_write_new();
|
||||
if (a == NULL) {
|
||||
msg("archive_write_new() failed.\n");
|
||||
goto err;
|
||||
}
|
||||
|
||||
archive_ctxt->archive = a;
|
||||
archive_ctxt->dest_file = NULL;
|
||||
|
||||
if(archive_write_add_filter_none(a) != ARCHIVE_OK ||
|
||||
archive_write_set_format_pax_restricted(a) != ARCHIVE_OK ||
|
||||
/* disable internal buffering so we don't have to flush the
|
||||
output in xtrabackup */
|
||||
archive_write_set_bytes_per_block(a, 0) != ARCHIVE_OK) {
|
||||
msg("failed to set libarchive archive options: %s\n",
|
||||
archive_error_string(a));
|
||||
archive_write_free(a);
|
||||
goto err;
|
||||
}
|
||||
|
||||
if (archive_write_open(a, archive_ctxt, my_archive_open_callback,
|
||||
my_archive_write_callback,
|
||||
my_archive_close_callback) != ARCHIVE_OK) {
|
||||
msg("cannot open output archive.\n");
|
||||
return NULL;
|
||||
}
|
||||
|
||||
ctxt->ptr = archive_ctxt;
|
||||
|
||||
return ctxt;
|
||||
|
||||
err:
|
||||
my_free(ctxt);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
static
|
||||
ds_file_t *
|
||||
archive_open(ds_ctxt_t *ctxt, const char *path, MY_STAT *mystat)
|
||||
{
|
||||
ds_archive_ctxt_t *archive_ctxt;
|
||||
ds_ctxt_t *dest_ctxt;
|
||||
ds_file_t *file;
|
||||
ds_archive_file_t *archive_file;
|
||||
|
||||
struct archive *a;
|
||||
struct archive_entry *entry;
|
||||
|
||||
xb_ad(ctxt->pipe_ctxt != NULL);
|
||||
dest_ctxt = ctxt->pipe_ctxt;
|
||||
|
||||
archive_ctxt = (ds_archive_ctxt_t *) ctxt->ptr;
|
||||
|
||||
pthread_mutex_lock(&archive_ctxt->mutex);
|
||||
if (archive_ctxt->dest_file == NULL) {
|
||||
archive_ctxt->dest_file = ds_open(dest_ctxt, path, mystat);
|
||||
if (archive_ctxt->dest_file == NULL) {
|
||||
return NULL;
|
||||
}
|
||||
}
|
||||
pthread_mutex_unlock(&archive_ctxt->mutex);
|
||||
|
||||
file = (ds_file_t *) my_malloc(sizeof(ds_file_t) +
|
||||
sizeof(ds_archive_file_t),
|
||||
MYF(MY_FAE));
|
||||
|
||||
archive_file = (ds_archive_file_t *) (file + 1);
|
||||
|
||||
a = archive_ctxt->archive;
|
||||
|
||||
entry = archive_entry_new();
|
||||
if (entry == NULL) {
|
||||
msg("archive_entry_new() failed.\n");
|
||||
goto err;
|
||||
}
|
||||
|
||||
archive_entry_set_size(entry, mystat->st_size);
|
||||
archive_entry_set_mode(entry, 0660);
|
||||
archive_entry_set_filetype(entry, AE_IFREG);
|
||||
archive_entry_set_pathname(entry, path);
|
||||
archive_entry_set_mtime(entry, mystat->st_mtime, 0);
|
||||
|
||||
archive_file->entry = entry;
|
||||
archive_file->archive_ctxt = archive_ctxt;
|
||||
|
||||
if (archive_write_header(a, entry) != ARCHIVE_OK) {
|
||||
msg("archive_write_header() failed.\n");
|
||||
archive_entry_free(entry);
|
||||
goto err;
|
||||
}
|
||||
|
||||
file->ptr = archive_file;
|
||||
file->path = archive_ctxt->dest_file->path;
|
||||
|
||||
return file;
|
||||
|
||||
err:
|
||||
if (archive_ctxt->dest_file) {
|
||||
ds_close(archive_ctxt->dest_file);
|
||||
archive_ctxt->dest_file = NULL;
|
||||
}
|
||||
my_free(file);
|
||||
|
||||
return NULL;
|
||||
}
|
||||
|
||||
static
|
||||
int
|
||||
archive_write(ds_file_t *file, const void *buf, size_t len)
|
||||
{
|
||||
ds_archive_file_t *archive_file;
|
||||
struct archive *a;
|
||||
|
||||
archive_file = (ds_archive_file_t *) file->ptr;
|
||||
|
||||
a = archive_file->archive_ctxt->archive;
|
||||
|
||||
xb_ad(archive_file->archive_ctxt->dest_file != NULL);
|
||||
if (archive_write_data(a, buf, len) < 0) {
|
||||
msg("archive_write_data() failed: %s (errno = %d)\n",
|
||||
archive_error_string(a), archive_errno(a));
|
||||
return 1;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static
|
||||
int
|
||||
archive_close(ds_file_t *file)
|
||||
{
|
||||
ds_archive_file_t *archive_file;
|
||||
int rc = 0;
|
||||
|
||||
archive_file = (ds_archive_file_t *)file->ptr;
|
||||
|
||||
archive_entry_free(archive_file->entry);
|
||||
|
||||
my_free(file);
|
||||
|
||||
return rc;
|
||||
}
|
||||
|
||||
static
|
||||
void
|
||||
archive_deinit(ds_ctxt_t *ctxt)
|
||||
{
|
||||
struct archive *a;
|
||||
ds_archive_ctxt_t *archive_ctxt;
|
||||
|
||||
archive_ctxt = (ds_archive_ctxt_t *) ctxt->ptr;
|
||||
|
||||
a = archive_ctxt->archive;
|
||||
|
||||
if (archive_write_close(a) != ARCHIVE_OK) {
|
||||
msg("archive_write_close() failed.\n");
|
||||
}
|
||||
archive_write_free(a);
|
||||
|
||||
if (archive_ctxt->dest_file) {
|
||||
ds_close(archive_ctxt->dest_file);
|
||||
archive_ctxt->dest_file = NULL;
|
||||
}
|
||||
|
||||
pthread_mutex_destroy(&archive_ctxt->mutex);
|
||||
|
||||
my_free(ctxt);
|
||||
}
|
28
extra/mariabackup/ds_archive.h
Normal file
28
extra/mariabackup/ds_archive.h
Normal file
|
@ -0,0 +1,28 @@
|
|||
/******************************************************
|
||||
Copyright (c) 2013 Percona LLC and/or its affiliates.
|
||||
|
||||
Streaming interface for XtraBackup.
|
||||
|
||||
This program is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; version 2 of the License.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with this program; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
|
||||
|
||||
*******************************************************/
|
||||
|
||||
#ifndef DS_ARCHIVE_H
|
||||
#define DS_ARCHIVE_H
|
||||
|
||||
#include "datasink.h"
|
||||
|
||||
extern datasink_t datasink_archive;
|
||||
|
||||
#endif
|
189
extra/mariabackup/ds_buffer.c
Normal file
189
extra/mariabackup/ds_buffer.c
Normal file
|
@ -0,0 +1,189 @@
|
|||
/******************************************************
|
||||
Copyright (c) 2012-2013 Percona LLC and/or its affiliates.
|
||||
|
||||
buffer datasink for XtraBackup.
|
||||
|
||||
This program is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; version 2 of the License.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with this program; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
|
||||
|
||||
*******************************************************/
|
||||
|
||||
/* Does buffered output to a destination datasink set with ds_set_pipe().
|
||||
Writes to the destination datasink are guaranteed to not be smaller than a
|
||||
specified buffer size (DS_DEFAULT_BUFFER_SIZE by default), with the only
|
||||
exception for the last write for a file. */
|
||||
|
||||
#include <mysql_version.h>
|
||||
#include <my_base.h>
|
||||
#include "ds_buffer.h"
|
||||
#include "common.h"
|
||||
#include "datasink.h"
|
||||
|
||||
#define DS_DEFAULT_BUFFER_SIZE (64 * 1024)
|
||||
|
||||
typedef struct {
|
||||
ds_file_t *dst_file;
|
||||
char *buf;
|
||||
size_t pos;
|
||||
size_t size;
|
||||
} ds_buffer_file_t;
|
||||
|
||||
typedef struct {
|
||||
size_t buffer_size;
|
||||
} ds_buffer_ctxt_t;
|
||||
|
||||
static ds_ctxt_t *buffer_init(const char *root);
|
||||
static ds_file_t *buffer_open(ds_ctxt_t *ctxt, const char *path,
|
||||
MY_STAT *mystat);
|
||||
static int buffer_write(ds_file_t *file, const void *buf, size_t len);
|
||||
static int buffer_close(ds_file_t *file);
|
||||
static void buffer_deinit(ds_ctxt_t *ctxt);
|
||||
|
||||
datasink_t datasink_buffer = {
|
||||
&buffer_init,
|
||||
&buffer_open,
|
||||
&buffer_write,
|
||||
&buffer_close,
|
||||
&buffer_deinit
|
||||
};
|
||||
|
||||
/* Change the default buffer size */
|
||||
void ds_buffer_set_size(ds_ctxt_t *ctxt, size_t size)
|
||||
{
|
||||
ds_buffer_ctxt_t *buffer_ctxt = (ds_buffer_ctxt_t *) ctxt->ptr;
|
||||
|
||||
buffer_ctxt->buffer_size = size;
|
||||
}
|
||||
|
||||
static ds_ctxt_t *
|
||||
buffer_init(const char *root)
|
||||
{
|
||||
ds_ctxt_t *ctxt;
|
||||
ds_buffer_ctxt_t *buffer_ctxt;
|
||||
|
||||
ctxt = my_malloc(sizeof(ds_ctxt_t) + sizeof(ds_buffer_ctxt_t),
|
||||
MYF(MY_FAE));
|
||||
buffer_ctxt = (ds_buffer_ctxt_t *) (ctxt + 1);
|
||||
buffer_ctxt->buffer_size = DS_DEFAULT_BUFFER_SIZE;
|
||||
|
||||
ctxt->ptr = buffer_ctxt;
|
||||
ctxt->root = my_strdup(root, MYF(MY_FAE));
|
||||
|
||||
return ctxt;
|
||||
}
|
||||
|
||||
static ds_file_t *
|
||||
buffer_open(ds_ctxt_t *ctxt, const char *path, MY_STAT *mystat)
|
||||
{
|
||||
ds_buffer_ctxt_t *buffer_ctxt;
|
||||
ds_ctxt_t *pipe_ctxt;
|
||||
ds_file_t *dst_file;
|
||||
ds_file_t *file;
|
||||
ds_buffer_file_t *buffer_file;
|
||||
|
||||
pipe_ctxt = ctxt->pipe_ctxt;
|
||||
xb_a(pipe_ctxt != NULL);
|
||||
|
||||
dst_file = ds_open(pipe_ctxt, path, mystat);
|
||||
if (dst_file == NULL) {
|
||||
exit(EXIT_FAILURE);
|
||||
}
|
||||
|
||||
buffer_ctxt = (ds_buffer_ctxt_t *) ctxt->ptr;
|
||||
|
||||
file = (ds_file_t *) my_malloc(sizeof(ds_file_t) +
|
||||
sizeof(ds_buffer_file_t) +
|
||||
buffer_ctxt->buffer_size,
|
||||
MYF(MY_FAE));
|
||||
|
||||
buffer_file = (ds_buffer_file_t *) (file + 1);
|
||||
buffer_file->dst_file = dst_file;
|
||||
buffer_file->buf = (char *) (buffer_file + 1);
|
||||
buffer_file->size = buffer_ctxt->buffer_size;
|
||||
buffer_file->pos = 0;
|
||||
|
||||
file->path = dst_file->path;
|
||||
file->ptr = buffer_file;
|
||||
|
||||
return file;
|
||||
}
|
||||
|
||||
static int
|
||||
buffer_write(ds_file_t *file, const void *buf, size_t len)
|
||||
{
|
||||
ds_buffer_file_t *buffer_file;
|
||||
|
||||
buffer_file = (ds_buffer_file_t *) file->ptr;
|
||||
|
||||
while (len > 0) {
|
||||
if (buffer_file->pos + len > buffer_file->size) {
|
||||
if (buffer_file->pos > 0) {
|
||||
size_t bytes;
|
||||
|
||||
bytes = buffer_file->size - buffer_file->pos;
|
||||
memcpy(buffer_file->buf + buffer_file->pos, buf,
|
||||
bytes);
|
||||
|
||||
if (ds_write(buffer_file->dst_file,
|
||||
buffer_file->buf,
|
||||
buffer_file->size)) {
|
||||
return 1;
|
||||
}
|
||||
|
||||
buffer_file->pos = 0;
|
||||
|
||||
buf = (const char *) buf + bytes;
|
||||
len -= bytes;
|
||||
} else {
|
||||
/* We don't have any buffered bytes, just write
|
||||
the entire source buffer */
|
||||
if (ds_write(buffer_file->dst_file, buf, len)) {
|
||||
return 1;
|
||||
}
|
||||
break;
|
||||
}
|
||||
} else {
|
||||
memcpy(buffer_file->buf + buffer_file->pos, buf, len);
|
||||
buffer_file->pos += len;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int
|
||||
buffer_close(ds_file_t *file)
|
||||
{
|
||||
ds_buffer_file_t *buffer_file;
|
||||
int ret;
|
||||
|
||||
buffer_file = (ds_buffer_file_t *) file->ptr;
|
||||
if (buffer_file->pos > 0) {
|
||||
ds_write(buffer_file->dst_file, buffer_file->buf,
|
||||
buffer_file->pos);
|
||||
}
|
||||
|
||||
ret = ds_close(buffer_file->dst_file);
|
||||
|
||||
my_free(file);
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
static void
|
||||
buffer_deinit(ds_ctxt_t *ctxt)
|
||||
{
|
||||
my_free(ctxt->root);
|
||||
my_free(ctxt);
|
||||
}
|
39
extra/mariabackup/ds_buffer.h
Normal file
39
extra/mariabackup/ds_buffer.h
Normal file
|
@ -0,0 +1,39 @@
|
|||
/******************************************************
|
||||
Copyright (c) 2012-2013 Percona LLC and/or its affiliates.
|
||||
|
||||
buffer datasink for XtraBackup.
|
||||
|
||||
This program is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; version 2 of the License.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with this program; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
|
||||
|
||||
*******************************************************/
|
||||
|
||||
#ifndef DS_BUFFER_H
|
||||
#define DS_BUFFER_H
|
||||
|
||||
#include "datasink.h"
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
extern datasink_t datasink_buffer;
|
||||
|
||||
/* Change the default buffer size */
|
||||
void ds_buffer_set_size(ds_ctxt_t *ctxt, size_t size);
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif
|
462
extra/mariabackup/ds_compress.c
Normal file
462
extra/mariabackup/ds_compress.c
Normal file
|
@ -0,0 +1,462 @@
|
|||
/******************************************************
|
||||
Copyright (c) 2011-2013 Percona LLC and/or its affiliates.
|
||||
|
||||
Compressing datasink implementation for XtraBackup.
|
||||
|
||||
This program is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; version 2 of the License.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with this program; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
|
||||
|
||||
*******************************************************/
|
||||
|
||||
#include <mysql_version.h>
|
||||
#include <my_base.h>
|
||||
#include <quicklz.h>
|
||||
#include <zlib.h>
|
||||
#include "common.h"
|
||||
#include "datasink.h"
|
||||
|
||||
#define COMPRESS_CHUNK_SIZE ((size_t) (xtrabackup_compress_chunk_size))
|
||||
#define MY_QLZ_COMPRESS_OVERHEAD 400
|
||||
|
||||
typedef struct {
|
||||
pthread_t id;
|
||||
uint num;
|
||||
pthread_mutex_t ctrl_mutex;
|
||||
pthread_cond_t ctrl_cond;
|
||||
pthread_mutex_t data_mutex;
|
||||
pthread_cond_t data_cond;
|
||||
my_bool started;
|
||||
my_bool data_avail;
|
||||
my_bool cancelled;
|
||||
const char *from;
|
||||
size_t from_len;
|
||||
char *to;
|
||||
size_t to_len;
|
||||
qlz_state_compress state;
|
||||
ulong adler;
|
||||
} comp_thread_ctxt_t;
|
||||
|
||||
typedef struct {
|
||||
comp_thread_ctxt_t *threads;
|
||||
uint nthreads;
|
||||
} ds_compress_ctxt_t;
|
||||
|
||||
typedef struct {
|
||||
ds_file_t *dest_file;
|
||||
ds_compress_ctxt_t *comp_ctxt;
|
||||
size_t bytes_processed;
|
||||
} ds_compress_file_t;
|
||||
|
||||
/* Compression options */
|
||||
extern char *xtrabackup_compress_alg;
|
||||
extern uint xtrabackup_compress_threads;
|
||||
extern ulonglong xtrabackup_compress_chunk_size;
|
||||
|
||||
static ds_ctxt_t *compress_init(const char *root);
|
||||
static ds_file_t *compress_open(ds_ctxt_t *ctxt, const char *path,
|
||||
MY_STAT *mystat);
|
||||
static int compress_write(ds_file_t *file, const void *buf, size_t len);
|
||||
static int compress_close(ds_file_t *file);
|
||||
static void compress_deinit(ds_ctxt_t *ctxt);
|
||||
|
||||
datasink_t datasink_compress = {
|
||||
&compress_init,
|
||||
&compress_open,
|
||||
&compress_write,
|
||||
&compress_close,
|
||||
&compress_deinit
|
||||
};
|
||||
|
||||
static inline int write_uint32_le(ds_file_t *file, ulong n);
|
||||
static inline int write_uint64_le(ds_file_t *file, ulonglong n);
|
||||
|
||||
static comp_thread_ctxt_t *create_worker_threads(uint n);
|
||||
static void destroy_worker_threads(comp_thread_ctxt_t *threads, uint n);
|
||||
static void *compress_worker_thread_func(void *arg);
|
||||
|
||||
static
|
||||
ds_ctxt_t *
|
||||
compress_init(const char *root)
|
||||
{
|
||||
ds_ctxt_t *ctxt;
|
||||
ds_compress_ctxt_t *compress_ctxt;
|
||||
comp_thread_ctxt_t *threads;
|
||||
|
||||
/* Create and initialize the worker threads */
|
||||
threads = create_worker_threads(xtrabackup_compress_threads);
|
||||
if (threads == NULL) {
|
||||
msg("compress: failed to create worker threads.\n");
|
||||
return NULL;
|
||||
}
|
||||
|
||||
ctxt = (ds_ctxt_t *) my_malloc(sizeof(ds_ctxt_t) +
|
||||
sizeof(ds_compress_ctxt_t),
|
||||
MYF(MY_FAE));
|
||||
|
||||
compress_ctxt = (ds_compress_ctxt_t *) (ctxt + 1);
|
||||
compress_ctxt->threads = threads;
|
||||
compress_ctxt->nthreads = xtrabackup_compress_threads;
|
||||
|
||||
ctxt->ptr = compress_ctxt;
|
||||
ctxt->root = my_strdup(root, MYF(MY_FAE));
|
||||
|
||||
return ctxt;
|
||||
}
|
||||
|
||||
static
|
||||
ds_file_t *
|
||||
compress_open(ds_ctxt_t *ctxt, const char *path, MY_STAT *mystat)
|
||||
{
|
||||
ds_compress_ctxt_t *comp_ctxt;
|
||||
ds_ctxt_t *dest_ctxt;
|
||||
ds_file_t *dest_file;
|
||||
char new_name[FN_REFLEN];
|
||||
size_t name_len;
|
||||
ds_file_t *file;
|
||||
ds_compress_file_t *comp_file;
|
||||
|
||||
xb_ad(ctxt->pipe_ctxt != NULL);
|
||||
dest_ctxt = ctxt->pipe_ctxt;
|
||||
|
||||
comp_ctxt = (ds_compress_ctxt_t *) ctxt->ptr;
|
||||
|
||||
/* Append the .qp extension to the filename */
|
||||
fn_format(new_name, path, "", ".qp", MYF(MY_APPEND_EXT));
|
||||
|
||||
dest_file = ds_open(dest_ctxt, new_name, mystat);
|
||||
if (dest_file == NULL) {
|
||||
return NULL;
|
||||
}
|
||||
|
||||
/* Write the qpress archive header */
|
||||
if (ds_write(dest_file, "qpress10", 8) ||
|
||||
write_uint64_le(dest_file, COMPRESS_CHUNK_SIZE)) {
|
||||
goto err;
|
||||
}
|
||||
|
||||
/* We are going to create a one-file "flat" (i.e. with no
|
||||
subdirectories) archive. So strip the directory part from the path and
|
||||
remove the '.qp' suffix. */
|
||||
fn_format(new_name, path, "", "", MYF(MY_REPLACE_DIR));
|
||||
|
||||
/* Write the qpress file header */
|
||||
name_len = strlen(new_name);
|
||||
if (ds_write(dest_file, "F", 1) ||
|
||||
write_uint32_le(dest_file, (uint)name_len) ||
|
||||
/* we want to write the terminating \0 as well */
|
||||
ds_write(dest_file, new_name, name_len + 1)) {
|
||||
goto err;
|
||||
}
|
||||
|
||||
file = (ds_file_t *) my_malloc(sizeof(ds_file_t) +
|
||||
sizeof(ds_compress_file_t),
|
||||
MYF(MY_FAE));
|
||||
comp_file = (ds_compress_file_t *) (file + 1);
|
||||
comp_file->dest_file = dest_file;
|
||||
comp_file->comp_ctxt = comp_ctxt;
|
||||
comp_file->bytes_processed = 0;
|
||||
|
||||
file->ptr = comp_file;
|
||||
file->path = dest_file->path;
|
||||
|
||||
return file;
|
||||
|
||||
err:
|
||||
ds_close(dest_file);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
static
|
||||
int
|
||||
compress_write(ds_file_t *file, const void *buf, size_t len)
|
||||
{
|
||||
ds_compress_file_t *comp_file;
|
||||
ds_compress_ctxt_t *comp_ctxt;
|
||||
comp_thread_ctxt_t *threads;
|
||||
comp_thread_ctxt_t *thd;
|
||||
uint nthreads;
|
||||
uint i;
|
||||
const char *ptr;
|
||||
ds_file_t *dest_file;
|
||||
|
||||
comp_file = (ds_compress_file_t *) file->ptr;
|
||||
comp_ctxt = comp_file->comp_ctxt;
|
||||
dest_file = comp_file->dest_file;
|
||||
|
||||
threads = comp_ctxt->threads;
|
||||
nthreads = comp_ctxt->nthreads;
|
||||
|
||||
ptr = (const char *) buf;
|
||||
while (len > 0) {
|
||||
uint max_thread;
|
||||
|
||||
/* Send data to worker threads for compression */
|
||||
for (i = 0; i < nthreads; i++) {
|
||||
size_t chunk_len;
|
||||
|
||||
thd = threads + i;
|
||||
|
||||
pthread_mutex_lock(&thd->ctrl_mutex);
|
||||
|
||||
chunk_len = (len > COMPRESS_CHUNK_SIZE) ?
|
||||
COMPRESS_CHUNK_SIZE : len;
|
||||
thd->from = ptr;
|
||||
thd->from_len = chunk_len;
|
||||
|
||||
pthread_mutex_lock(&thd->data_mutex);
|
||||
thd->data_avail = TRUE;
|
||||
pthread_cond_signal(&thd->data_cond);
|
||||
pthread_mutex_unlock(&thd->data_mutex);
|
||||
|
||||
len -= chunk_len;
|
||||
if (len == 0) {
|
||||
break;
|
||||
}
|
||||
ptr += chunk_len;
|
||||
}
|
||||
|
||||
max_thread = (i < nthreads) ? i : nthreads - 1;
|
||||
|
||||
/* Reap and stream the compressed data */
|
||||
for (i = 0; i <= max_thread; i++) {
|
||||
thd = threads + i;
|
||||
|
||||
pthread_mutex_lock(&thd->data_mutex);
|
||||
while (thd->data_avail == TRUE) {
|
||||
pthread_cond_wait(&thd->data_cond,
|
||||
&thd->data_mutex);
|
||||
}
|
||||
|
||||
xb_a(threads[i].to_len > 0);
|
||||
|
||||
if (ds_write(dest_file, "NEWBNEWB", 8) ||
|
||||
write_uint64_le(dest_file,
|
||||
comp_file->bytes_processed)) {
|
||||
msg("compress: write to the destination stream "
|
||||
"failed.\n");
|
||||
return 1;
|
||||
}
|
||||
|
||||
comp_file->bytes_processed += threads[i].from_len;
|
||||
|
||||
if (write_uint32_le(dest_file, threads[i].adler) ||
|
||||
ds_write(dest_file, threads[i].to,
|
||||
threads[i].to_len)) {
|
||||
msg("compress: write to the destination stream "
|
||||
"failed.\n");
|
||||
return 1;
|
||||
}
|
||||
|
||||
pthread_mutex_unlock(&threads[i].data_mutex);
|
||||
pthread_mutex_unlock(&threads[i].ctrl_mutex);
|
||||
}
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static
|
||||
int
|
||||
compress_close(ds_file_t *file)
|
||||
{
|
||||
ds_compress_file_t *comp_file;
|
||||
ds_file_t *dest_file;
|
||||
int rc;
|
||||
|
||||
comp_file = (ds_compress_file_t *) file->ptr;
|
||||
dest_file = comp_file->dest_file;
|
||||
|
||||
/* Write the qpress file trailer */
|
||||
ds_write(dest_file, "ENDSENDS", 8);
|
||||
|
||||
/* Supposedly the number of written bytes should be written as a
|
||||
"recovery information" in the file trailer, but in reality qpress
|
||||
always writes 8 zeros here. Let's do the same */
|
||||
|
||||
write_uint64_le(dest_file, 0);
|
||||
|
||||
rc = ds_close(dest_file);
|
||||
|
||||
my_free(file);
|
||||
|
||||
return rc;
|
||||
}
|
||||
|
||||
static
|
||||
void
|
||||
compress_deinit(ds_ctxt_t *ctxt)
|
||||
{
|
||||
ds_compress_ctxt_t *comp_ctxt;
|
||||
|
||||
xb_ad(ctxt->pipe_ctxt != NULL);
|
||||
|
||||
comp_ctxt = (ds_compress_ctxt_t *) ctxt->ptr;;
|
||||
|
||||
destroy_worker_threads(comp_ctxt->threads, comp_ctxt->nthreads);
|
||||
|
||||
my_free(ctxt->root);
|
||||
my_free(ctxt);
|
||||
}
|
||||
|
||||
static inline
|
||||
int
|
||||
write_uint32_le(ds_file_t *file, ulong n)
|
||||
{
|
||||
char tmp[4];
|
||||
|
||||
int4store(tmp, n);
|
||||
return ds_write(file, tmp, sizeof(tmp));
|
||||
}
|
||||
|
||||
static inline
|
||||
int
|
||||
write_uint64_le(ds_file_t *file, ulonglong n)
|
||||
{
|
||||
char tmp[8];
|
||||
|
||||
int8store(tmp, n);
|
||||
return ds_write(file, tmp, sizeof(tmp));
|
||||
}
|
||||
|
||||
static
|
||||
comp_thread_ctxt_t *
|
||||
create_worker_threads(uint n)
|
||||
{
|
||||
comp_thread_ctxt_t *threads;
|
||||
uint i;
|
||||
|
||||
threads = (comp_thread_ctxt_t *)
|
||||
my_malloc(sizeof(comp_thread_ctxt_t) * n, MYF(MY_FAE));
|
||||
|
||||
for (i = 0; i < n; i++) {
|
||||
comp_thread_ctxt_t *thd = threads + i;
|
||||
|
||||
thd->num = i + 1;
|
||||
thd->started = FALSE;
|
||||
thd->cancelled = FALSE;
|
||||
thd->data_avail = FALSE;
|
||||
|
||||
thd->to = (char *) my_malloc(COMPRESS_CHUNK_SIZE +
|
||||
MY_QLZ_COMPRESS_OVERHEAD,
|
||||
MYF(MY_FAE));
|
||||
|
||||
/* Initialize the control mutex and condition var */
|
||||
if (pthread_mutex_init(&thd->ctrl_mutex, NULL) ||
|
||||
pthread_cond_init(&thd->ctrl_cond, NULL)) {
|
||||
goto err;
|
||||
}
|
||||
|
||||
/* Initialize and data mutex and condition var */
|
||||
if (pthread_mutex_init(&thd->data_mutex, NULL) ||
|
||||
pthread_cond_init(&thd->data_cond, NULL)) {
|
||||
goto err;
|
||||
}
|
||||
|
||||
pthread_mutex_lock(&thd->ctrl_mutex);
|
||||
|
||||
if (pthread_create(&thd->id, NULL, compress_worker_thread_func,
|
||||
thd)) {
|
||||
msg("compress: pthread_create() failed: "
|
||||
"errno = %d\n", errno);
|
||||
goto err;
|
||||
}
|
||||
}
|
||||
|
||||
/* Wait for the threads to start */
|
||||
for (i = 0; i < n; i++) {
|
||||
comp_thread_ctxt_t *thd = threads + i;
|
||||
|
||||
while (thd->started == FALSE)
|
||||
pthread_cond_wait(&thd->ctrl_cond, &thd->ctrl_mutex);
|
||||
pthread_mutex_unlock(&thd->ctrl_mutex);
|
||||
}
|
||||
|
||||
return threads;
|
||||
|
||||
err:
|
||||
return NULL;
|
||||
}
|
||||
|
||||
static
|
||||
void
|
||||
destroy_worker_threads(comp_thread_ctxt_t *threads, uint n)
|
||||
{
|
||||
uint i;
|
||||
|
||||
for (i = 0; i < n; i++) {
|
||||
comp_thread_ctxt_t *thd = threads + i;
|
||||
|
||||
pthread_mutex_lock(&thd->data_mutex);
|
||||
threads[i].cancelled = TRUE;
|
||||
pthread_cond_signal(&thd->data_cond);
|
||||
pthread_mutex_unlock(&thd->data_mutex);
|
||||
|
||||
pthread_join(thd->id, NULL);
|
||||
|
||||
pthread_cond_destroy(&thd->data_cond);
|
||||
pthread_mutex_destroy(&thd->data_mutex);
|
||||
pthread_cond_destroy(&thd->ctrl_cond);
|
||||
pthread_mutex_destroy(&thd->ctrl_mutex);
|
||||
|
||||
my_free(thd->to);
|
||||
}
|
||||
|
||||
my_free(threads);
|
||||
}
|
||||
|
||||
static
|
||||
void *
|
||||
compress_worker_thread_func(void *arg)
|
||||
{
|
||||
comp_thread_ctxt_t *thd = (comp_thread_ctxt_t *) arg;
|
||||
|
||||
pthread_mutex_lock(&thd->ctrl_mutex);
|
||||
|
||||
pthread_mutex_lock(&thd->data_mutex);
|
||||
|
||||
thd->started = TRUE;
|
||||
pthread_cond_signal(&thd->ctrl_cond);
|
||||
|
||||
pthread_mutex_unlock(&thd->ctrl_mutex);
|
||||
|
||||
while (1) {
|
||||
thd->data_avail = FALSE;
|
||||
pthread_cond_signal(&thd->data_cond);
|
||||
|
||||
while (!thd->data_avail && !thd->cancelled) {
|
||||
pthread_cond_wait(&thd->data_cond, &thd->data_mutex);
|
||||
}
|
||||
|
||||
if (thd->cancelled)
|
||||
break;
|
||||
|
||||
thd->to_len = qlz_compress(thd->from, thd->to, thd->from_len,
|
||||
&thd->state);
|
||||
|
||||
/* qpress uses 0x00010000 as the initial value, but its own
|
||||
Adler-32 implementation treats the value differently:
|
||||
1. higher order bits are the sum of all bytes in the sequence
|
||||
2. lower order bits are the sum of resulting values at every
|
||||
step.
|
||||
So it's the other way around as compared to zlib's adler32().
|
||||
That's why 0x00000001 is being passed here to be compatible
|
||||
with qpress implementation. */
|
||||
|
||||
thd->adler = adler32(0x00000001, (uchar *) thd->to,
|
||||
(uInt)thd->to_len);
|
||||
}
|
||||
|
||||
pthread_mutex_unlock(&thd->data_mutex);
|
||||
|
||||
return NULL;
|
||||
}
|
28
extra/mariabackup/ds_compress.h
Normal file
28
extra/mariabackup/ds_compress.h
Normal file
|
@ -0,0 +1,28 @@
|
|||
/******************************************************
|
||||
Copyright (c) 2011-2013 Percona LLC and/or its affiliates.
|
||||
|
||||
Compression interface for XtraBackup.
|
||||
|
||||
This program is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; version 2 of the License.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with this program; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
|
||||
|
||||
*******************************************************/
|
||||
|
||||
#ifndef DS_COMPRESS_H
|
||||
#define DS_COMPRESS_H
|
||||
|
||||
#include "datasink.h"
|
||||
|
||||
extern datasink_t datasink_compress;
|
||||
|
||||
#endif
|
151
extra/mariabackup/ds_local.c
Normal file
151
extra/mariabackup/ds_local.c
Normal file
|
@ -0,0 +1,151 @@
|
|||
/******************************************************
|
||||
Copyright (c) 2011-2013 Percona LLC and/or its affiliates.
|
||||
|
||||
Local datasink implementation for XtraBackup.
|
||||
|
||||
This program is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; version 2 of the License.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with this program; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
|
||||
|
||||
*******************************************************/
|
||||
|
||||
#include <mysql_version.h>
|
||||
#include <my_base.h>
|
||||
#include <mysys_err.h>
|
||||
#include "common.h"
|
||||
#include "datasink.h"
|
||||
|
||||
typedef struct {
|
||||
File fd;
|
||||
} ds_local_file_t;
|
||||
|
||||
static ds_ctxt_t *local_init(const char *root);
|
||||
static ds_file_t *local_open(ds_ctxt_t *ctxt, const char *path,
|
||||
MY_STAT *mystat);
|
||||
static int local_write(ds_file_t *file, const void *buf, size_t len);
|
||||
static int local_close(ds_file_t *file);
|
||||
static void local_deinit(ds_ctxt_t *ctxt);
|
||||
|
||||
datasink_t datasink_local = {
|
||||
&local_init,
|
||||
&local_open,
|
||||
&local_write,
|
||||
&local_close,
|
||||
&local_deinit
|
||||
};
|
||||
|
||||
static
|
||||
ds_ctxt_t *
|
||||
local_init(const char *root)
|
||||
{
|
||||
ds_ctxt_t *ctxt;
|
||||
|
||||
if (my_mkdir(root, 0777, MYF(0)) < 0
|
||||
&& my_errno != EEXIST && my_errno != EISDIR)
|
||||
{
|
||||
char errbuf[MYSYS_STRERROR_SIZE];
|
||||
my_strerror(errbuf, sizeof(errbuf),my_errno);
|
||||
my_error(EE_CANT_MKDIR, MYF(ME_BELL | ME_WAITTANG),
|
||||
root, my_errno,errbuf, my_errno);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
ctxt = my_malloc(sizeof(ds_ctxt_t), MYF(MY_FAE));
|
||||
|
||||
ctxt->root = my_strdup(root, MYF(MY_FAE));
|
||||
|
||||
return ctxt;
|
||||
}
|
||||
|
||||
static
|
||||
ds_file_t *
|
||||
local_open(ds_ctxt_t *ctxt, const char *path,
|
||||
MY_STAT *mystat __attribute__((unused)))
|
||||
{
|
||||
char fullpath[FN_REFLEN];
|
||||
char dirpath[FN_REFLEN];
|
||||
size_t dirpath_len;
|
||||
size_t path_len;
|
||||
ds_local_file_t *local_file;
|
||||
ds_file_t *file;
|
||||
File fd;
|
||||
|
||||
fn_format(fullpath, path, ctxt->root, "", MYF(MY_RELATIVE_PATH));
|
||||
|
||||
/* Create the directory if needed */
|
||||
dirname_part(dirpath, fullpath, &dirpath_len);
|
||||
if (my_mkdir(dirpath, 0777, MYF(0)) < 0 && my_errno != EEXIST) {
|
||||
char errbuf[MYSYS_STRERROR_SIZE];
|
||||
my_strerror(errbuf, sizeof(errbuf), my_errno);
|
||||
my_error(EE_CANT_MKDIR, MYF(ME_BELL | ME_WAITTANG),
|
||||
dirpath, my_errno, errbuf);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
fd = my_create(fullpath, 0, O_WRONLY | O_BINARY | O_EXCL | O_NOFOLLOW,
|
||||
MYF(MY_WME));
|
||||
if (fd < 0) {
|
||||
return NULL;
|
||||
}
|
||||
|
||||
path_len = strlen(fullpath) + 1; /* terminating '\0' */
|
||||
|
||||
file = (ds_file_t *) my_malloc(sizeof(ds_file_t) +
|
||||
sizeof(ds_local_file_t) +
|
||||
path_len,
|
||||
MYF(MY_FAE));
|
||||
local_file = (ds_local_file_t *) (file + 1);
|
||||
|
||||
local_file->fd = fd;
|
||||
|
||||
file->path = (char *) local_file + sizeof(ds_local_file_t);
|
||||
memcpy(file->path, fullpath, path_len);
|
||||
|
||||
file->ptr = local_file;
|
||||
|
||||
return file;
|
||||
}
|
||||
|
||||
static
|
||||
int
|
||||
local_write(ds_file_t *file, const void *buf, size_t len)
|
||||
{
|
||||
File fd = ((ds_local_file_t *) file->ptr)->fd;
|
||||
|
||||
if (!my_write(fd, buf, len, MYF(MY_WME | MY_NABP))) {
|
||||
posix_fadvise(fd, 0, 0, POSIX_FADV_DONTNEED);
|
||||
return 0;
|
||||
}
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
static
|
||||
int
|
||||
local_close(ds_file_t *file)
|
||||
{
|
||||
File fd = ((ds_local_file_t *) file->ptr)->fd;
|
||||
|
||||
my_free(file);
|
||||
|
||||
my_sync(fd, MYF(MY_WME));
|
||||
|
||||
return my_close(fd, MYF(MY_WME));
|
||||
}
|
||||
|
||||
static
|
||||
void
|
||||
local_deinit(ds_ctxt_t *ctxt)
|
||||
{
|
||||
my_free(ctxt->root);
|
||||
my_free(ctxt);
|
||||
}
|
28
extra/mariabackup/ds_local.h
Normal file
28
extra/mariabackup/ds_local.h
Normal file
|
@ -0,0 +1,28 @@
|
|||
/******************************************************
|
||||
Copyright (c) 2011-2013 Percona LLC and/or its affiliates.
|
||||
|
||||
Local datasink interface for XtraBackup.
|
||||
|
||||
This program is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; version 2 of the License.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with this program; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
|
||||
|
||||
*******************************************************/
|
||||
|
||||
#ifndef DS_LOCAL_H
|
||||
#define DS_LOCAL_H
|
||||
|
||||
#include "datasink.h"
|
||||
|
||||
extern datasink_t datasink_local;
|
||||
|
||||
#endif
|
121
extra/mariabackup/ds_stdout.c
Normal file
121
extra/mariabackup/ds_stdout.c
Normal file
|
@ -0,0 +1,121 @@
|
|||
/******************************************************
|
||||
Copyright (c) 2013 Percona LLC and/or its affiliates.
|
||||
|
||||
Local datasink implementation for XtraBackup.
|
||||
|
||||
This program is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; version 2 of the License.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with this program; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
|
||||
|
||||
*******************************************************/
|
||||
|
||||
#include <my_base.h>
|
||||
#include <mysys_err.h>
|
||||
#include "common.h"
|
||||
#include "datasink.h"
|
||||
|
||||
typedef struct {
|
||||
File fd;
|
||||
} ds_stdout_file_t;
|
||||
|
||||
static ds_ctxt_t *stdout_init(const char *root);
|
||||
static ds_file_t *stdout_open(ds_ctxt_t *ctxt, const char *path,
|
||||
MY_STAT *mystat);
|
||||
static int stdout_write(ds_file_t *file, const void *buf, size_t len);
|
||||
static int stdout_close(ds_file_t *file);
|
||||
static void stdout_deinit(ds_ctxt_t *ctxt);
|
||||
|
||||
datasink_t datasink_stdout = {
|
||||
&stdout_init,
|
||||
&stdout_open,
|
||||
&stdout_write,
|
||||
&stdout_close,
|
||||
&stdout_deinit
|
||||
};
|
||||
|
||||
static
|
||||
ds_ctxt_t *
|
||||
stdout_init(const char *root)
|
||||
{
|
||||
ds_ctxt_t *ctxt;
|
||||
|
||||
ctxt = my_malloc(sizeof(ds_ctxt_t), MYF(MY_FAE));
|
||||
|
||||
ctxt->root = my_strdup(root, MYF(MY_FAE));
|
||||
|
||||
return ctxt;
|
||||
}
|
||||
|
||||
static
|
||||
ds_file_t *
|
||||
stdout_open(ds_ctxt_t *ctxt __attribute__((unused)),
|
||||
const char *path __attribute__((unused)),
|
||||
MY_STAT *mystat __attribute__((unused)))
|
||||
{
|
||||
ds_stdout_file_t *stdout_file;
|
||||
ds_file_t *file;
|
||||
size_t pathlen;
|
||||
const char *fullpath = "<STDOUT>";
|
||||
|
||||
pathlen = strlen(fullpath) + 1;
|
||||
|
||||
file = (ds_file_t *) my_malloc(sizeof(ds_file_t) +
|
||||
sizeof(ds_stdout_file_t) +
|
||||
pathlen,
|
||||
MYF(MY_FAE));
|
||||
stdout_file = (ds_stdout_file_t *) (file + 1);
|
||||
|
||||
|
||||
#ifdef __WIN__
|
||||
setmode(fileno(stdout), _O_BINARY);
|
||||
#endif
|
||||
|
||||
stdout_file->fd = my_fileno(stdout);
|
||||
|
||||
file->path = (char *) stdout_file + sizeof(ds_stdout_file_t);
|
||||
memcpy(file->path, fullpath, pathlen);
|
||||
|
||||
file->ptr = stdout_file;
|
||||
|
||||
return file;
|
||||
}
|
||||
|
||||
static
|
||||
int
|
||||
stdout_write(ds_file_t *file, const void *buf, size_t len)
|
||||
{
|
||||
File fd = ((ds_stdout_file_t *) file->ptr)->fd;
|
||||
|
||||
if (!my_write(fd, buf, len, MYF(MY_WME | MY_NABP))) {
|
||||
posix_fadvise(fd, 0, 0, POSIX_FADV_DONTNEED);
|
||||
return 0;
|
||||
}
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
static
|
||||
int
|
||||
stdout_close(ds_file_t *file)
|
||||
{
|
||||
my_free(file);
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
static
|
||||
void
|
||||
stdout_deinit(ds_ctxt_t *ctxt)
|
||||
{
|
||||
my_free(ctxt->root);
|
||||
my_free(ctxt);
|
||||
}
|
28
extra/mariabackup/ds_stdout.h
Normal file
28
extra/mariabackup/ds_stdout.h
Normal file
|
@ -0,0 +1,28 @@
|
|||
/******************************************************
|
||||
Copyright (c) 2013 Percona LLC and/or its affiliates.
|
||||
|
||||
Local datasink interface for XtraBackup.
|
||||
|
||||
This program is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; version 2 of the License.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with this program; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
|
||||
|
||||
*******************************************************/
|
||||
|
||||
#ifndef DS_STDOUT_H
|
||||
#define DS_STDOUT_H
|
||||
|
||||
#include "datasink.h"
|
||||
|
||||
extern datasink_t datasink_stdout;
|
||||
|
||||
#endif
|
247
extra/mariabackup/ds_tmpfile.c
Normal file
247
extra/mariabackup/ds_tmpfile.c
Normal file
|
@ -0,0 +1,247 @@
|
|||
/******************************************************
|
||||
Copyright (c) 2012 Percona LLC and/or its affiliates.
|
||||
|
||||
tmpfile datasink for XtraBackup.
|
||||
|
||||
This program is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; version 2 of the License.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with this program; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
|
||||
|
||||
*******************************************************/
|
||||
|
||||
/* Do all writes to temporary files first, then pipe them to the specified
|
||||
datasink in a serialized way in deinit(). */
|
||||
|
||||
#include <my_base.h>
|
||||
#include "common.h"
|
||||
#include "datasink.h"
|
||||
|
||||
typedef struct {
|
||||
pthread_mutex_t mutex;
|
||||
LIST *file_list;
|
||||
} ds_tmpfile_ctxt_t;
|
||||
|
||||
typedef struct {
|
||||
LIST list;
|
||||
File fd;
|
||||
char *orig_path;
|
||||
MY_STAT mystat;
|
||||
ds_file_t *file;
|
||||
} ds_tmp_file_t;
|
||||
|
||||
static ds_ctxt_t *tmpfile_init(const char *root);
|
||||
static ds_file_t *tmpfile_open(ds_ctxt_t *ctxt, const char *path,
|
||||
MY_STAT *mystat);
|
||||
static int tmpfile_write(ds_file_t *file, const void *buf, size_t len);
|
||||
static int tmpfile_close(ds_file_t *file);
|
||||
static void tmpfile_deinit(ds_ctxt_t *ctxt);
|
||||
|
||||
datasink_t datasink_tmpfile = {
|
||||
&tmpfile_init,
|
||||
&tmpfile_open,
|
||||
&tmpfile_write,
|
||||
&tmpfile_close,
|
||||
&tmpfile_deinit
|
||||
};
|
||||
|
||||
|
||||
static ds_ctxt_t *
|
||||
tmpfile_init(const char *root)
|
||||
{
|
||||
ds_ctxt_t *ctxt;
|
||||
ds_tmpfile_ctxt_t *tmpfile_ctxt;
|
||||
|
||||
ctxt = my_malloc(sizeof(ds_ctxt_t) + sizeof(ds_tmpfile_ctxt_t),
|
||||
MYF(MY_FAE));
|
||||
tmpfile_ctxt = (ds_tmpfile_ctxt_t *) (ctxt + 1);
|
||||
tmpfile_ctxt->file_list = NULL;
|
||||
if (pthread_mutex_init(&tmpfile_ctxt->mutex, NULL)) {
|
||||
|
||||
my_free(ctxt);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
ctxt->ptr = tmpfile_ctxt;
|
||||
ctxt->root = my_strdup(root, MYF(MY_FAE));
|
||||
|
||||
return ctxt;
|
||||
}
|
||||
|
||||
static ds_file_t *
|
||||
tmpfile_open(ds_ctxt_t *ctxt, const char *path,
|
||||
MY_STAT *mystat)
|
||||
{
|
||||
ds_tmpfile_ctxt_t *tmpfile_ctxt;
|
||||
char tmp_path[FN_REFLEN];
|
||||
ds_tmp_file_t *tmp_file;
|
||||
ds_file_t *file;
|
||||
size_t path_len;
|
||||
File fd;
|
||||
|
||||
/* Create a temporary file in tmpdir. The file will be automatically
|
||||
removed on close. Code copied from mysql_tmpfile(). */
|
||||
fd = create_temp_file(tmp_path,xtrabackup_tmpdir,
|
||||
"xbtemp",
|
||||
#ifdef __WIN__
|
||||
O_BINARY | O_TRUNC | O_SEQUENTIAL |
|
||||
O_TEMPORARY | O_SHORT_LIVED |
|
||||
#endif /* __WIN__ */
|
||||
O_CREAT | O_EXCL | O_RDWR,
|
||||
MYF(MY_WME));
|
||||
|
||||
#ifndef __WIN__
|
||||
if (fd >= 0) {
|
||||
/* On Windows, open files cannot be removed, but files can be
|
||||
created with the O_TEMPORARY flag to the same effect
|
||||
("delete on close"). */
|
||||
unlink(tmp_path);
|
||||
}
|
||||
#endif /* !__WIN__ */
|
||||
|
||||
if (fd < 0) {
|
||||
return NULL;
|
||||
}
|
||||
|
||||
path_len = strlen(path) + 1; /* terminating '\0' */
|
||||
|
||||
file = (ds_file_t *) my_malloc(sizeof(ds_file_t) +
|
||||
sizeof(ds_tmp_file_t) + path_len,
|
||||
MYF(MY_FAE));
|
||||
|
||||
tmp_file = (ds_tmp_file_t *) (file + 1);
|
||||
tmp_file->file = file;
|
||||
memcpy(&tmp_file->mystat, mystat, sizeof(MY_STAT));
|
||||
/* Save a copy of 'path', since it may not be accessible later */
|
||||
tmp_file->orig_path = (char *) tmp_file + sizeof(ds_tmp_file_t);
|
||||
|
||||
tmp_file->fd = fd;
|
||||
memcpy(tmp_file->orig_path, path, path_len);
|
||||
|
||||
/* Store the real temporary file name in file->path */
|
||||
file->path = my_strdup(tmp_path, MYF(MY_FAE));
|
||||
file->ptr = tmp_file;
|
||||
|
||||
/* Store the file object in the list to be piped later */
|
||||
tmpfile_ctxt = (ds_tmpfile_ctxt_t *) ctxt->ptr;
|
||||
tmp_file->list.data = tmp_file;
|
||||
|
||||
pthread_mutex_lock(&tmpfile_ctxt->mutex);
|
||||
tmpfile_ctxt->file_list = list_add(tmpfile_ctxt->file_list,
|
||||
&tmp_file->list);
|
||||
pthread_mutex_unlock(&tmpfile_ctxt->mutex);
|
||||
|
||||
return file;
|
||||
}
|
||||
|
||||
static int
|
||||
tmpfile_write(ds_file_t *file, const void *buf, size_t len)
|
||||
{
|
||||
File fd = ((ds_tmp_file_t *) file->ptr)->fd;
|
||||
|
||||
if (!my_write(fd, buf, len, MYF(MY_WME | MY_NABP))) {
|
||||
posix_fadvise(fd, 0, 0, POSIX_FADV_DONTNEED);
|
||||
return 0;
|
||||
}
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
static int
|
||||
tmpfile_close(ds_file_t *file)
|
||||
{
|
||||
/* Do nothing -- we will close (and thus remove) the file after piping
|
||||
it to the destination datasink in tmpfile_deinit(). */
|
||||
|
||||
my_free(file->path);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static void
|
||||
tmpfile_deinit(ds_ctxt_t *ctxt)
|
||||
{
|
||||
LIST *list;
|
||||
ds_tmpfile_ctxt_t *tmpfile_ctxt;
|
||||
MY_STAT mystat;
|
||||
ds_tmp_file_t *tmp_file;
|
||||
ds_file_t *dst_file;
|
||||
ds_ctxt_t *pipe_ctxt;
|
||||
void *buf = NULL;
|
||||
const size_t buf_size = 10 * 1024 * 1024;
|
||||
size_t bytes;
|
||||
size_t offset;
|
||||
|
||||
pipe_ctxt = ctxt->pipe_ctxt;
|
||||
xb_a(pipe_ctxt != NULL);
|
||||
|
||||
buf = my_malloc(buf_size, MYF(MY_FAE));
|
||||
|
||||
tmpfile_ctxt = (ds_tmpfile_ctxt_t *) ctxt->ptr;
|
||||
list = tmpfile_ctxt->file_list;
|
||||
|
||||
/* Walk the files in the order they have been added */
|
||||
list = list_reverse(list);
|
||||
while (list != NULL) {
|
||||
tmp_file = list->data;
|
||||
/* Stat the file to replace size and mtime on the original
|
||||
* mystat struct */
|
||||
if (my_fstat(tmp_file->fd, &mystat, MYF(0))) {
|
||||
msg("error: my_fstat() failed.\n");
|
||||
exit(EXIT_FAILURE);
|
||||
}
|
||||
tmp_file->mystat.st_size = mystat.st_size;
|
||||
tmp_file->mystat.st_mtime = mystat.st_mtime;
|
||||
|
||||
dst_file = ds_open(pipe_ctxt, tmp_file->orig_path,
|
||||
&tmp_file->mystat);
|
||||
if (dst_file == NULL) {
|
||||
msg("error: could not stream a temporary file to "
|
||||
"'%s'\n", tmp_file->orig_path);
|
||||
exit(EXIT_FAILURE);
|
||||
}
|
||||
|
||||
/* copy to the destination datasink */
|
||||
posix_fadvise(tmp_file->fd, 0, 0, POSIX_FADV_SEQUENTIAL);
|
||||
if (my_seek(tmp_file->fd, 0, SEEK_SET, MYF(0)) ==
|
||||
MY_FILEPOS_ERROR) {
|
||||
msg("error: my_seek() failed for '%s', errno = %d.\n",
|
||||
tmp_file->file->path, my_errno);
|
||||
exit(EXIT_FAILURE);
|
||||
}
|
||||
offset = 0;
|
||||
while ((bytes = my_read(tmp_file->fd, buf, buf_size,
|
||||
MYF(MY_WME))) > 0) {
|
||||
posix_fadvise(tmp_file->fd, offset, buf_size, POSIX_FADV_DONTNEED);
|
||||
offset += buf_size;
|
||||
if (ds_write(dst_file, buf, bytes)) {
|
||||
msg("error: cannot write to stream for '%s'.\n",
|
||||
tmp_file->orig_path);
|
||||
exit(EXIT_FAILURE);
|
||||
}
|
||||
}
|
||||
if (bytes == (size_t) -1) {
|
||||
exit(EXIT_FAILURE);
|
||||
}
|
||||
|
||||
my_close(tmp_file->fd, MYF(MY_WME));
|
||||
ds_close(dst_file);
|
||||
|
||||
list = list_rest(list);
|
||||
my_free(tmp_file->file);
|
||||
}
|
||||
|
||||
pthread_mutex_destroy(&tmpfile_ctxt->mutex);
|
||||
|
||||
my_free(buf);
|
||||
my_free(ctxt->root);
|
||||
my_free(ctxt);
|
||||
}
|
30
extra/mariabackup/ds_tmpfile.h
Normal file
30
extra/mariabackup/ds_tmpfile.h
Normal file
|
@ -0,0 +1,30 @@
|
|||
/******************************************************
|
||||
Copyright (c) 2012 Percona LLC and/or its affiliates.
|
||||
|
||||
tmpfile datasink for XtraBackup.
|
||||
|
||||
This program is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; version 2 of the License.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with this program; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
|
||||
|
||||
*******************************************************/
|
||||
|
||||
#ifndef DS_TMPFILE_H
|
||||
#define DS_TMPFILE_H
|
||||
|
||||
#include "datasink.h"
|
||||
|
||||
extern datasink_t datasink_tmpfile;
|
||||
|
||||
extern MY_TMPDIR mysql_tmpdir_list;
|
||||
|
||||
#endif
|
223
extra/mariabackup/ds_xbstream.c
Normal file
223
extra/mariabackup/ds_xbstream.c
Normal file
|
@ -0,0 +1,223 @@
|
|||
/******************************************************
|
||||
Copyright (c) 2011-2013 Percona LLC and/or its affiliates.
|
||||
|
||||
Streaming implementation for XtraBackup.
|
||||
|
||||
This program is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; version 2 of the License.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with this program; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
|
||||
|
||||
*******************************************************/
|
||||
|
||||
#include <mysql_version.h>
|
||||
#include <my_base.h>
|
||||
#include "common.h"
|
||||
#include "datasink.h"
|
||||
#include "xbstream.h"
|
||||
|
||||
typedef struct {
|
||||
xb_wstream_t *xbstream;
|
||||
ds_file_t *dest_file;
|
||||
pthread_mutex_t mutex;
|
||||
} ds_stream_ctxt_t;
|
||||
|
||||
typedef struct {
|
||||
xb_wstream_file_t *xbstream_file;
|
||||
ds_stream_ctxt_t *stream_ctxt;
|
||||
} ds_stream_file_t;
|
||||
|
||||
/***********************************************************************
|
||||
General streaming interface */
|
||||
|
||||
static ds_ctxt_t *xbstream_init(const char *root);
|
||||
static ds_file_t *xbstream_open(ds_ctxt_t *ctxt, const char *path,
|
||||
MY_STAT *mystat);
|
||||
static int xbstream_write(ds_file_t *file, const void *buf, size_t len);
|
||||
static int xbstream_close(ds_file_t *file);
|
||||
static void xbstream_deinit(ds_ctxt_t *ctxt);
|
||||
|
||||
datasink_t datasink_xbstream = {
|
||||
&xbstream_init,
|
||||
&xbstream_open,
|
||||
&xbstream_write,
|
||||
&xbstream_close,
|
||||
&xbstream_deinit
|
||||
};
|
||||
|
||||
static
|
||||
ssize_t
|
||||
my_xbstream_write_callback(xb_wstream_file_t *f __attribute__((unused)),
|
||||
void *userdata, const void *buf, size_t len)
|
||||
{
|
||||
ds_stream_ctxt_t *stream_ctxt;
|
||||
|
||||
stream_ctxt = (ds_stream_ctxt_t *) userdata;
|
||||
|
||||
xb_ad(stream_ctxt != NULL);
|
||||
xb_ad(stream_ctxt->dest_file != NULL);
|
||||
|
||||
if (!ds_write(stream_ctxt->dest_file, buf, len)) {
|
||||
return len;
|
||||
}
|
||||
return -1;
|
||||
}
|
||||
|
||||
static
|
||||
ds_ctxt_t *
|
||||
xbstream_init(const char *root __attribute__((unused)))
|
||||
{
|
||||
ds_ctxt_t *ctxt;
|
||||
ds_stream_ctxt_t *stream_ctxt;
|
||||
xb_wstream_t *xbstream;
|
||||
|
||||
ctxt = my_malloc(sizeof(ds_ctxt_t) + sizeof(ds_stream_ctxt_t),
|
||||
MYF(MY_FAE));
|
||||
stream_ctxt = (ds_stream_ctxt_t *)(ctxt + 1);
|
||||
|
||||
if (pthread_mutex_init(&stream_ctxt->mutex, NULL)) {
|
||||
msg("xbstream_init: pthread_mutex_init() failed.\n");
|
||||
goto err;
|
||||
}
|
||||
|
||||
xbstream = xb_stream_write_new();
|
||||
if (xbstream == NULL) {
|
||||
msg("xb_stream_write_new() failed.\n");
|
||||
goto err;
|
||||
}
|
||||
stream_ctxt->xbstream = xbstream;
|
||||
stream_ctxt->dest_file = NULL;
|
||||
|
||||
ctxt->ptr = stream_ctxt;
|
||||
|
||||
return ctxt;
|
||||
|
||||
err:
|
||||
my_free(ctxt);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
static
|
||||
ds_file_t *
|
||||
xbstream_open(ds_ctxt_t *ctxt, const char *path, MY_STAT *mystat)
|
||||
{
|
||||
ds_file_t *file;
|
||||
ds_stream_file_t *stream_file;
|
||||
ds_stream_ctxt_t *stream_ctxt;
|
||||
ds_ctxt_t *dest_ctxt;
|
||||
xb_wstream_t *xbstream;
|
||||
xb_wstream_file_t *xbstream_file;
|
||||
|
||||
|
||||
xb_ad(ctxt->pipe_ctxt != NULL);
|
||||
dest_ctxt = ctxt->pipe_ctxt;
|
||||
|
||||
stream_ctxt = (ds_stream_ctxt_t *) ctxt->ptr;
|
||||
|
||||
pthread_mutex_lock(&stream_ctxt->mutex);
|
||||
if (stream_ctxt->dest_file == NULL) {
|
||||
stream_ctxt->dest_file = ds_open(dest_ctxt, path, mystat);
|
||||
if (stream_ctxt->dest_file == NULL) {
|
||||
return NULL;
|
||||
}
|
||||
}
|
||||
pthread_mutex_unlock(&stream_ctxt->mutex);
|
||||
|
||||
file = (ds_file_t *) my_malloc(sizeof(ds_file_t) +
|
||||
sizeof(ds_stream_file_t),
|
||||
MYF(MY_FAE));
|
||||
stream_file = (ds_stream_file_t *) (file + 1);
|
||||
|
||||
xbstream = stream_ctxt->xbstream;
|
||||
|
||||
xbstream_file = xb_stream_write_open(xbstream, path, mystat,
|
||||
stream_ctxt,
|
||||
my_xbstream_write_callback);
|
||||
|
||||
if (xbstream_file == NULL) {
|
||||
msg("xb_stream_write_open() failed.\n");
|
||||
goto err;
|
||||
}
|
||||
|
||||
stream_file->xbstream_file = xbstream_file;
|
||||
stream_file->stream_ctxt = stream_ctxt;
|
||||
file->ptr = stream_file;
|
||||
file->path = stream_ctxt->dest_file->path;
|
||||
|
||||
return file;
|
||||
|
||||
err:
|
||||
if (stream_ctxt->dest_file) {
|
||||
ds_close(stream_ctxt->dest_file);
|
||||
stream_ctxt->dest_file = NULL;
|
||||
}
|
||||
my_free(file);
|
||||
|
||||
return NULL;
|
||||
}
|
||||
|
||||
static
|
||||
int
|
||||
xbstream_write(ds_file_t *file, const void *buf, size_t len)
|
||||
{
|
||||
ds_stream_file_t *stream_file;
|
||||
xb_wstream_file_t *xbstream_file;
|
||||
|
||||
|
||||
stream_file = (ds_stream_file_t *) file->ptr;
|
||||
|
||||
xbstream_file = stream_file->xbstream_file;
|
||||
|
||||
if (xb_stream_write_data(xbstream_file, buf, len)) {
|
||||
msg("xb_stream_write_data() failed.\n");
|
||||
return 1;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static
|
||||
int
|
||||
xbstream_close(ds_file_t *file)
|
||||
{
|
||||
ds_stream_file_t *stream_file;
|
||||
int rc = 0;
|
||||
|
||||
stream_file = (ds_stream_file_t *)file->ptr;
|
||||
|
||||
rc = xb_stream_write_close(stream_file->xbstream_file);
|
||||
|
||||
my_free(file);
|
||||
|
||||
return rc;
|
||||
}
|
||||
|
||||
static
|
||||
void
|
||||
xbstream_deinit(ds_ctxt_t *ctxt)
|
||||
{
|
||||
ds_stream_ctxt_t *stream_ctxt;
|
||||
|
||||
stream_ctxt = (ds_stream_ctxt_t *) ctxt->ptr;
|
||||
|
||||
if (xb_stream_write_done(stream_ctxt->xbstream)) {
|
||||
msg("xb_stream_done() failed.\n");
|
||||
}
|
||||
|
||||
if (stream_ctxt->dest_file) {
|
||||
ds_close(stream_ctxt->dest_file);
|
||||
stream_ctxt->dest_file = NULL;
|
||||
}
|
||||
|
||||
pthread_mutex_destroy(&stream_ctxt->mutex);
|
||||
|
||||
my_free(ctxt);
|
||||
}
|
28
extra/mariabackup/ds_xbstream.h
Normal file
28
extra/mariabackup/ds_xbstream.h
Normal file
|
@ -0,0 +1,28 @@
|
|||
/******************************************************
|
||||
Copyright (c) 2011-2013 Percona LLC and/or its affiliates.
|
||||
|
||||
Streaming interface for XtraBackup.
|
||||
|
||||
This program is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; version 2 of the License.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with this program; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
|
||||
|
||||
*******************************************************/
|
||||
|
||||
#ifndef DS_XBSTREAM_H
|
||||
#define DS_XBSTREAM_H
|
||||
|
||||
#include "datasink.h"
|
||||
|
||||
extern datasink_t datasink_xbstream;
|
||||
|
||||
#endif
|
157
extra/mariabackup/encryption_plugin.cc
Normal file
157
extra/mariabackup/encryption_plugin.cc
Normal file
|
@ -0,0 +1,157 @@
|
|||
#include <mysqld.h>
|
||||
#include <mysql.h>
|
||||
#include <xtrabackup.h>
|
||||
#include <encryption_plugin.h>
|
||||
#include <backup_copy.h>
|
||||
#include <sql_plugin.h>
|
||||
#include <sstream>
|
||||
#include <vector>
|
||||
#include <common.h>
|
||||
#include <backup_mysql.h>
|
||||
#include <log0crypt.h>
|
||||
|
||||
|
||||
extern struct st_maria_plugin *mysql_optional_plugins[];
|
||||
extern struct st_maria_plugin *mysql_mandatory_plugins[];
|
||||
static void encryption_plugin_init(int argc, char **argv);
|
||||
|
||||
extern char *xb_plugin_load;
|
||||
extern char *xb_plugin_dir;
|
||||
|
||||
const int PLUGIN_MAX_ARGS = 1024;
|
||||
std::vector<std::string> backup_plugins_args;
|
||||
|
||||
const char *QUERY_PLUGIN =
|
||||
"SELECT plugin_name, plugin_library, @@plugin_dir"
|
||||
" FROM information_schema.plugins WHERE plugin_type='ENCRYPTION'"
|
||||
" AND plugin_status='ACTIVE'";
|
||||
|
||||
std::string encryption_plugin_config;
|
||||
|
||||
static void add_to_plugin_load_list(const char *plugin_def)
|
||||
{
|
||||
opt_plugin_load_list_ptr->push_back(new i_string(plugin_def));
|
||||
}
|
||||
|
||||
static char XTRABACKUP_EXE[] = "xtrabackup";
|
||||
|
||||
void encryption_plugin_backup_init(MYSQL *mysql)
|
||||
{
|
||||
MYSQL_RES *result;
|
||||
MYSQL_ROW row;
|
||||
std::ostringstream oss;
|
||||
char *argv[PLUGIN_MAX_ARGS];
|
||||
int argc;
|
||||
|
||||
result = xb_mysql_query(mysql, QUERY_PLUGIN, true, true);
|
||||
row = mysql_fetch_row(result);
|
||||
if (!row)
|
||||
{
|
||||
mysql_free_result(result);
|
||||
return;
|
||||
}
|
||||
|
||||
char *name= row[0];
|
||||
char *library= row[1];
|
||||
char *dir= row[2];
|
||||
|
||||
#ifdef _WIN32
|
||||
for (char *p = dir; *p; p++)
|
||||
if (*p == '\\') *p = '/';
|
||||
#endif
|
||||
|
||||
std::string plugin_load(name);
|
||||
if (library)
|
||||
plugin_load += std::string("=") + library;
|
||||
|
||||
oss << "plugin_load=" << plugin_load << std::endl;
|
||||
|
||||
/* Required to load the plugin later.*/
|
||||
add_to_plugin_load_list(plugin_load.c_str());
|
||||
strncpy(opt_plugin_dir, dir, FN_REFLEN);
|
||||
|
||||
oss << "plugin_dir=" << '"' << dir << '"' << std::endl;
|
||||
|
||||
|
||||
/* Read plugin variables. */
|
||||
char query[1024];
|
||||
snprintf(query, 1024, "SHOW variables like '%s_%%'", name);
|
||||
mysql_free_result(result);
|
||||
|
||||
result = xb_mysql_query(mysql, query, true, true);
|
||||
while ((row = mysql_fetch_row(result)))
|
||||
{
|
||||
std::string arg("--");
|
||||
arg += row[0];
|
||||
arg += "=";
|
||||
arg += row[1];
|
||||
backup_plugins_args.push_back(arg);
|
||||
oss << row[0] << "=" << row[1] << std::endl;
|
||||
}
|
||||
|
||||
mysql_free_result(result);
|
||||
|
||||
/* Check whether to encrypt logs. */
|
||||
result = xb_mysql_query(mysql, "select @@innodb_encrypt_log", true, true);
|
||||
row = mysql_fetch_row(result);
|
||||
srv_encrypt_log = (row != 0 && row[0][0] == '1');
|
||||
oss << "innodb_encrypt_log=" << row[0] << std::endl;
|
||||
|
||||
mysql_free_result(result);
|
||||
|
||||
encryption_plugin_config = oss.str();
|
||||
|
||||
argc = 0;
|
||||
argv[argc++] = XTRABACKUP_EXE;
|
||||
for(size_t i = 0; i < backup_plugins_args.size(); i++)
|
||||
{
|
||||
argv[argc++] = (char *)backup_plugins_args[i].c_str();
|
||||
if (argc == PLUGIN_MAX_ARGS - 2)
|
||||
break;
|
||||
}
|
||||
argv[argc] = 0;
|
||||
|
||||
encryption_plugin_init(argc, argv);
|
||||
}
|
||||
|
||||
const char *encryption_plugin_get_config()
|
||||
{
|
||||
return encryption_plugin_config.c_str();
|
||||
}
|
||||
|
||||
extern int finalize_encryption_plugin(st_plugin_int *plugin);
|
||||
|
||||
|
||||
void encryption_plugin_prepare_init(int argc, char **argv)
|
||||
{
|
||||
|
||||
if (!xb_plugin_load)
|
||||
{
|
||||
finalize_encryption_plugin(0);
|
||||
return;
|
||||
}
|
||||
|
||||
add_to_plugin_load_list(xb_plugin_load);
|
||||
|
||||
if (xb_plugin_dir)
|
||||
strncpy(opt_plugin_dir, xb_plugin_dir, FN_REFLEN);
|
||||
|
||||
char **new_argv = new char *[argc + 1];
|
||||
new_argv[0] = XTRABACKUP_EXE;
|
||||
memcpy(&new_argv[1], argv, argc*sizeof(char *));
|
||||
|
||||
encryption_plugin_init(argc+1, new_argv);
|
||||
|
||||
delete[] new_argv;
|
||||
}
|
||||
|
||||
static void encryption_plugin_init(int argc, char **argv)
|
||||
{
|
||||
/* Patch optional and mandatory plugins, we only need to load the one in xb_plugin_load. */
|
||||
mysql_optional_plugins[0] = mysql_mandatory_plugins[0] = 0;
|
||||
msg("Loading encryption plugin\n");
|
||||
for (int i= 1; i < argc; i++)
|
||||
msg("\t Encryption plugin parameter : '%s'\n", argv[i]);
|
||||
plugin_init(&argc, argv, PLUGIN_INIT_SKIP_PLUGIN_TABLE);
|
||||
}
|
||||
|
Some files were not shown because too many files have changed in this diff Show more
Loading…
Reference in a new issue