diff --git a/BUILD/SETUP.sh b/BUILD/SETUP.sh index e947df15e8e..0defa2d41f1 100755 --- a/BUILD/SETUP.sh +++ b/BUILD/SETUP.sh @@ -126,8 +126,10 @@ get_make_parallel_flag # SSL library to use.--with-ssl will select our bundled yaSSL # implementation of SSL. --with-ssl=yes will first try system library # then the bundled one --with-ssl=system will use the system library. -# We use bundled by default as this is guaranteed to work with Galera -SSL_LIBRARY=--with-ssl=bundled +# We normally use bundled by default as this is guaranteed to work with Galera +# However as bundled gives problem on SuSE with tls_version1.test, system +# is used +SSL_LIBRARY=--with-ssl=system if [ "x$warning_mode" = "xpedantic" ]; then warnings="-W -Wall -ansi -pedantic -Wno-long-long -Wno-unused -D_POSIX_SOURCE" diff --git a/CMakeLists.txt b/CMakeLists.txt index 9b8023bb6ba..ba1f422f602 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -195,6 +195,15 @@ ENDIF() OPTION(NOT_FOR_DISTRIBUTION "Allow linking with GPLv2-incompatible system libraries. Only set it you never plan to distribute the resulting binaries" OFF) +# +# Enable protection of statement's memory root after first SP/PS execution. +# Can be switched on only for debug build. +# +OPTION(WITH_PROTECT_STATEMENT_MEMROOT "Enable protection of statement's memory root after first SP/PS execution. Turned into account only for debug build" OFF) +IF (CMAKE_BUILD_TYPE MATCHES "Debug" AND WITH_PROTECT_STATEMENT_MEMROOT) + ADD_DEFINITIONS(-DPROTECT_STATEMENT_MEMROOT) +ENDIF() + INCLUDE(check_compiler_flag) INCLUDE(check_linker_flag) diff --git a/client/mysqlbinlog.cc b/client/mysqlbinlog.cc index 8929d733f06..bd33c15dca1 100644 --- a/client/mysqlbinlog.cc +++ b/client/mysqlbinlog.cc @@ -1640,7 +1640,7 @@ static struct my_option my_options[] = "given sequence numbers are printed.", &stop_pos_str, &stop_pos_str, 0, GET_STR_ALLOC, REQUIRED_ARG, 0, 0, 0, 0, 0, 0}, - {"table", 'T', "List entries for just this table (local log only).", + {"table", 'T', "List entries for just this table (affects only row events).", &table, &table, 0, GET_STR_ALLOC, REQUIRED_ARG, 0, 0, 0, 0, 0, 0}, {"to-last-log", 't', "Requires -R. Will not stop at the end of the \ diff --git a/client/mysqltest.cc b/client/mysqltest.cc index 6e40f4fa87a..4b34ef63615 100644 --- a/client/mysqltest.cc +++ b/client/mysqltest.cc @@ -1038,35 +1038,38 @@ exit_func: static int do_stmt_prepare(struct st_connection *cn, const char *q, int q_len) { /* The cn->stmt is already set. */ + DBUG_ENTER("do_stmt_prepare"); if (!cn->has_thread) - return mysql_stmt_prepare(cn->stmt, q, q_len); + DBUG_RETURN(mysql_stmt_prepare(cn->stmt, q, q_len)); cn->cur_query= q; cn->cur_query_len= q_len; signal_connection_thd(cn, EMB_PREPARE_STMT); wait_query_thread_done(cn); - return cn->result; + DBUG_RETURN(cn->result); } static int do_stmt_execute(struct st_connection *cn) { + DBUG_ENTER("do_stmt_execute"); /* The cn->stmt is already set. */ if (!cn->has_thread) - return mysql_stmt_execute(cn->stmt); + DBUG_RETURN(mysql_stmt_execute(cn->stmt)); signal_connection_thd(cn, EMB_EXECUTE_STMT); wait_query_thread_done(cn); - return cn->result; + DBUG_RETURN(cn->result); } static int do_stmt_close(struct st_connection *cn) { + DBUG_ENTER("do_stmt_close"); /* The cn->stmt is already set. */ if (!cn->has_thread) - return mysql_stmt_close(cn->stmt); + DBUG_RETURN(mysql_stmt_close(cn->stmt)); signal_connection_thd(cn, EMB_CLOSE_STMT); wait_query_thread_done(cn); - return cn->result; + DBUG_RETURN(cn->result); } @@ -7995,6 +7998,7 @@ int append_warnings(DYNAMIC_STRING *ds, MYSQL* mysql) if (!(count= mysql_warning_count(mysql))) DBUG_RETURN(0); + DBUG_PRINT("info", ("Warnings: %ud", count)); /* If one day we will support execution of multi-statements @@ -8450,6 +8454,7 @@ void run_query_stmt(struct st_connection *cn, struct st_command *command, char *query, size_t query_len, DYNAMIC_STRING *ds, DYNAMIC_STRING *ds_warnings) { + my_bool ignore_second_execution= 0; MYSQL_RES *res= NULL; /* Note that here 'res' is meta data result set */ MYSQL *mysql= cn->mysql; MYSQL_STMT *stmt; @@ -8457,6 +8462,9 @@ void run_query_stmt(struct st_connection *cn, struct st_command *command, DYNAMIC_STRING ds_execute_warnings; DBUG_ENTER("run_query_stmt"); DBUG_PRINT("query", ("'%-.60s'", query)); + DBUG_PRINT("info", + ("disable_warnings: %d prepare_warnings_enabled: %d", + (int) disable_warnings, (int) prepare_warnings_enabled)); if (!mysql) { @@ -8527,12 +8535,18 @@ void run_query_stmt(struct st_connection *cn, struct st_command *command, mysql_stmt_error(stmt), mysql_stmt_sqlstate(stmt), ds); goto end; } + /* + We cannot run query twice if we get prepare warnings as these will otherwise be + disabled + */ + ignore_second_execution= (prepare_warnings_enabled && + mysql_warning_count(mysql) != 0); } /* Execute the query */ - if (do_stmt_execute(cn)) + if (!ignore_second_execution && do_stmt_execute(cn)) { handle_error(command, mysql_stmt_errno(stmt), mysql_stmt_error(stmt), mysql_stmt_sqlstate(stmt), ds); @@ -8607,7 +8621,10 @@ void run_query_stmt(struct st_connection *cn, struct st_command *command, that warnings from both the prepare and execute phase are shown. */ if (!disable_warnings && !prepare_warnings_enabled) + { + DBUG_PRINT("info", ("warnings disabled")); dynstr_set(&ds_prepare_warnings, NULL); + } } else { @@ -8710,7 +8727,9 @@ end: error - function will not return */ -void run_prepare_stmt(struct st_connection *cn, struct st_command *command, const char *query, size_t query_len, DYNAMIC_STRING *ds, DYNAMIC_STRING *ds_warnings) +void run_prepare_stmt(struct st_connection *cn, struct st_command *command, + const char *query, size_t query_len, DYNAMIC_STRING *ds, + DYNAMIC_STRING *ds_warnings) { MYSQL *mysql= cn->mysql; @@ -8871,9 +8890,8 @@ void run_bind_stmt(struct st_connection *cn, struct st_command *command, */ void run_execute_stmt(struct st_connection *cn, struct st_command *command, - const char *query, size_t query_len, DYNAMIC_STRING *ds, - DYNAMIC_STRING *ds_warnings - ) + const char *query, size_t query_len, DYNAMIC_STRING *ds, + DYNAMIC_STRING *ds_warnings) { MYSQL_RES *res= NULL; /* Note that here 'res' is meta data result set */ MYSQL *mysql= cn->mysql; diff --git a/cmake/stack_direction.c b/cmake/stack_direction.c deleted file mode 100644 index 1f7a5d0b135..00000000000 --- a/cmake/stack_direction.c +++ /dev/null @@ -1,33 +0,0 @@ -/* - Copyright (c) 2009 Sun Microsystems, Inc. - 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 St, Fifth Floor, Boston, MA 02110-1335 USA */ - -/* Check stack direction (0-down, 1-up) */ -int f(int *a) -{ - int b; - return(&b > a)?1:0; -} -/* - Prevent compiler optimizations by calling function - through pointer. -*/ -volatile int (*ptr_f)(int *) = f; -int main() -{ - int a; - return ptr_f(&a); -} diff --git a/configure.cmake b/configure.cmake index b13d527742b..dbd77a6e00f 100644 --- a/configure.cmake +++ b/configure.cmake @@ -672,25 +672,11 @@ int main() } " HAVE_PTHREAD_YIELD_ZERO_ARG) -IF(NOT STACK_DIRECTION) - IF(CMAKE_CROSSCOMPILING AND NOT DEFINED CMAKE_CROSSCOMPILING_EMULATOR) - MESSAGE(FATAL_ERROR - "STACK_DIRECTION is not defined. Please specify -DSTACK_DIRECTION=1 " - "or -DSTACK_DIRECTION=-1 when calling cmake.") - ELSE() - TRY_RUN(STACKDIR_RUN_RESULT STACKDIR_COMPILE_RESULT - ${CMAKE_BINARY_DIR} - ${CMAKE_SOURCE_DIR}/cmake/stack_direction.c - ) - # Test program returns 0 (down) or 1 (up). - # Convert to -1 or 1 - IF(STACKDIR_RUN_RESULT EQUAL 0) - SET(STACK_DIRECTION -1 CACHE INTERNAL "Stack grows direction") - ELSE() - SET(STACK_DIRECTION 1 CACHE INTERNAL "Stack grows direction") - ENDIF() - MESSAGE(STATUS "Checking stack direction : ${STACK_DIRECTION}") - ENDIF() +IF(STACK_DIRECTION) +ELSEIF(CMAKE_SYSTEM_PROCESSOR MATCHES "^(parisc|hppa)") + SET(STACK_DIRECTION 1 CACHE INTERNAL "Stack grows direction") +ELSE() + SET(STACK_DIRECTION -1 CACHE INTERNAL "Stack grows direction") ENDIF() # diff --git a/debian/additions/mariadb.conf.d/50-server.cnf b/debian/additions/mariadb.conf.d/50-server.cnf index 0c0de595fe3..90ecafc7298 100644 --- a/debian/additions/mariadb.conf.d/50-server.cnf +++ b/debian/additions/mariadb.conf.d/50-server.cnf @@ -84,10 +84,10 @@ expire_logs_days = 10 # * Character sets # -# MySQL/MariaDB default is Latin1, but in Debian we rather default to the full +# MariaDB default is Latin1, but in Debian we rather default to the full # utf8 4-byte character set. See also client.cnf -character-set-server = utf8mb4 -collation-server = utf8mb4_general_ci +character-set-server = utf8mb4 +character-set-collations = utf8mb4=uca1400_ai_ci # # * InnoDB diff --git a/debian/rules b/debian/rules index 08ca3b8f96e..10915411a45 100755 --- a/debian/rules +++ b/debian/rules @@ -51,16 +51,6 @@ ifeq (32,$(DEB_HOST_ARCH_BITS)) CMAKEFLAGS += -DPLUGIN_ROCKSDB=NO endif -# Cross building requires stack direction instruction -ifneq ($(DEB_BUILD_ARCH),$(DEB_HOST_ARCH)) - ifneq (,$(filter $(DEB_HOST_ARCH_CPU),alpha amd64 arm arm64 i386 ia64 m68k mips64el mipsel powerpc ppc64 ppc64el riscv64 s390x sh4 sparc64)) - CMAKEFLAGS += -DSTACK_DIRECTION=-1 - endif - ifneq (,$(filter $(DEB_HOST_ARCH_CPU),hppa)) - CMAKEFLAGS += -DSTACK_DIRECTION=1 - endif -endif - # Only attempt to build with PMEM on archs that have package libpmem-dev available # See https://packages.debian.org/search?searchon=names&keywords=libpmem-dev ifneq (,$(filter $(DEB_HOST_ARCH),amd64 arm64 ppc64el riscv64)) diff --git a/extra/mariabackup/backup_copy.cc b/extra/mariabackup/backup_copy.cc index 1827601dae0..5b4bb35d63e 100644 --- a/extra/mariabackup/backup_copy.cc +++ b/extra/mariabackup/backup_copy.cc @@ -2298,7 +2298,7 @@ ds_ctxt_t::make_hardlink(const char *from_path, const char *to_path) } else { - strncpy(to_path_full, to_path, sizeof(to_path_full)); + strmake(to_path_full, to_path, sizeof(to_path_full)-1); } #ifdef _WIN32 return CreateHardLink(to_path_full, from_path, NULL); diff --git a/extra/mariabackup/xtrabackup.cc b/extra/mariabackup/xtrabackup.cc index 6a17f0034ae..3c530e9aef3 100644 --- a/extra/mariabackup/xtrabackup.cc +++ b/extra/mariabackup/xtrabackup.cc @@ -80,6 +80,7 @@ Street, Fifth Floor, Boston, MA 02110-1335 USA #include #include "trx0sys.h" #include +#include #include "ha_innodb.h" #include @@ -2385,10 +2386,15 @@ static bool innodb_init() buf_flush_sync(); recv_sys.debug_free(); ut_ad(!os_aio_pending_reads()); - ut_ad(!os_aio_pending_writes()); ut_d(mysql_mutex_lock(&buf_pool.flush_list_mutex)); ut_ad(!buf_pool.get_oldest_modification(0)); ut_d(mysql_mutex_unlock(&buf_pool.flush_list_mutex)); + /* os_aio_pending_writes() may hold here if some write_io_callback() + did not release the slot yet. However, the page write itself must + have completed, because the buf_pool.flush_list is empty. In debug + builds, we wait for this to happen, hoping to get a hung process if + this assumption does not hold. */ + ut_d(os_aio_wait_until_no_pending_writes(false)); log_sys.close_file(); if (xtrabackup_incremental) @@ -4693,7 +4699,9 @@ fail: goto fail; } - log_sys.create(); + if (!log_sys.create()) { + goto fail; + } /* get current checkpoint_lsn */ { mysql_mutex_lock(&recv_sys.mutex); @@ -6057,7 +6065,9 @@ error: } recv_sys.create(); - log_sys.create(); + if (!log_sys.create()) { + goto error; + } recv_sys.recovery_on = true; xb_fil_io_init(); diff --git a/extra/wolfssl/CMakeLists.txt b/extra/wolfssl/CMakeLists.txt index c034db01ce2..271e76b8c45 100644 --- a/extra/wolfssl/CMakeLists.txt +++ b/extra/wolfssl/CMakeLists.txt @@ -102,6 +102,9 @@ ${WOLFCRYPT_SRCDIR}/rsa.c ${WOLFCRYPT_SRCDIR}/sha.c ${WOLFCRYPT_SRCDIR}/sha256.c ${WOLFCRYPT_SRCDIR}/sha512.c +${WOLFCRYPT_SRCDIR}/poly1305.c +${WOLFCRYPT_SRCDIR}/chacha.c +${WOLFCRYPT_SRCDIR}/chacha20_poly1305.c ${WOLFCRYPT_SRCDIR}/wc_port.c ${WOLFCRYPT_SRCDIR}/wc_encrypt.c ${WOLFCRYPT_SRCDIR}/hash.c @@ -159,6 +162,8 @@ IF(WOLFSSL_X86_64_BUILD) LIST(APPEND WOLFCRYPT_SOURCES ${WOLFCRYPT_SRCDIR}/aes_asm.S ${WOLFCRYPT_SRCDIR}/aes_gcm_asm.S + ${WOLFCRYPT_SRCDIR}/chacha_asm.S + ${WOLFCRYPT_SRCDIR}/poly1305_asm.S ${WOLFCRYPT_SRCDIR}/sha512_asm.S ${WOLFCRYPT_SRCDIR}/sha256_asm.S) ADD_DEFINITIONS(-maes -msse4.2 -mpclmul) diff --git a/extra/wolfssl/user_settings.h.in b/extra/wolfssl/user_settings.h.in index 2355fd1691c..425f6f154b9 100644 --- a/extra/wolfssl/user_settings.h.in +++ b/extra/wolfssl/user_settings.h.in @@ -19,11 +19,15 @@ #define HAVE_TLS_EXTENSIONS #define HAVE_AES_ECB #define HAVE_AESGCM +#define HAVE_CHACHA +#define HAVE_POLY1305 #define WOLFSSL_AES_COUNTER #define NO_WOLFSSL_STUB #define OPENSSL_ALL #define WOLFSSL_ALLOW_TLSV10 #define NO_OLD_TIMEVAL_NAME +#define HAVE_SECURE_RENEGOTIATION +#define HAVE_EXTENDED_MASTER /* TLSv1.3 definitions (all needed to build) */ #define WOLFSSL_TLS13 diff --git a/include/m_ctype.h b/include/m_ctype.h index 0a825053868..9d13989d1fe 100644 --- a/include/m_ctype.h +++ b/include/m_ctype.h @@ -1021,6 +1021,12 @@ struct charset_info_st return (coll->strnncollsp)(this, (uchar *) a, alen, (uchar *) b, blen); } + int strnncollsp(const LEX_CSTRING &a, const LEX_CSTRING &b) const + { + return (coll->strnncollsp)(this, (uchar *) a.str, a.length, + (uchar *) b.str, b.length); + } + size_t strnxfrm(char *dst, size_t dstlen, uint nweights, const char *src, size_t srclen, uint flags) const { diff --git a/include/my_alloc.h b/include/my_alloc.h index 944dcb6e1bd..caa4be8f0e5 100644 --- a/include/my_alloc.h +++ b/include/my_alloc.h @@ -53,6 +53,10 @@ typedef struct st_mem_root unsigned short first_block_usage; unsigned short flags; +#ifdef PROTECT_STATEMENT_MEMROOT + int read_only; +#endif + void (*error_handler)(void); PSI_memory_key psi_key; diff --git a/include/my_sys.h b/include/my_sys.h index 6d2fd3e827e..2852d73d734 100644 --- a/include/my_sys.h +++ b/include/my_sys.h @@ -161,6 +161,7 @@ extern my_thread_id (*sf_malloc_dbug_id)(void); typedef void (*MALLOC_SIZE_CB) (long long size, my_bool is_thread_specific); extern void set_malloc_size_cb(MALLOC_SIZE_CB func); +extern MALLOC_SIZE_CB update_malloc_size; /* defines when allocating data */ extern void *my_malloc(PSI_memory_key key, size_t size, myf MyFlags); @@ -900,6 +901,8 @@ extern void free_root(MEM_ROOT *root, myf MyFLAGS); extern void set_prealloc_root(MEM_ROOT *root, char *ptr); extern void reset_root_defaults(MEM_ROOT *mem_root, size_t block_size, size_t prealloc_size); +extern USED_MEM *get_last_memroot_block(MEM_ROOT* root); +extern void free_all_new_blocks(MEM_ROOT *root, USED_MEM *last_block); extern void protect_root(MEM_ROOT *root, int prot); extern char *strdup_root(MEM_ROOT *root,const char *str); static inline char *safe_strdup_root(MEM_ROOT *root, const char *str) @@ -908,6 +911,7 @@ static inline char *safe_strdup_root(MEM_ROOT *root, const char *str) } extern char *strmake_root(MEM_ROOT *root,const char *str,size_t len); extern void *memdup_root(MEM_ROOT *root,const void *str, size_t len); + extern LEX_CSTRING safe_lexcstrdup_root(MEM_ROOT *root, const LEX_CSTRING str); static inline LEX_STRING lex_string_strmake_root(MEM_ROOT *mem_root, diff --git a/include/mysql.h b/include/mysql.h index 031570a0fe5..a66dcc7bd02 100644 --- a/include/mysql.h +++ b/include/mysql.h @@ -141,7 +141,6 @@ typedef unsigned long long my_ulonglong; #define ER_WRONG_FK_OPTION_FOR_VIRTUAL_COLUMN ER_WRONG_FK_OPTION_FOR_GENERATED_COLUMN #define ER_UNSUPPORTED_ACTION_ON_VIRTUAL_COLUMN ER_UNSUPPORTED_ACTION_ON_GENERATED_COLUMN #define ER_UNSUPPORTED_ENGINE_FOR_VIRTUAL_COLUMNS ER_UNSUPPORTED_ENGINE_FOR_GENERATED_COLUMNS -#define ER_QUERY_EXCEEDED_ROWS_EXAMINED_LIMIT ER_QUERY_RESULT_INCOMPLETE #define ER_KEY_COLUMN_DOES_NOT_EXITS ER_KEY_COLUMN_DOES_NOT_EXIST #define ER_DROP_PARTITION_NON_EXISTENT ER_PARTITION_DOES_NOT_EXIST diff --git a/include/mysql/service_my_crypt.h b/include/mysql/service_my_crypt.h index bb038aaa295..1a4ebcfd067 100644 --- a/include/mysql/service_my_crypt.h +++ b/include/mysql/service_my_crypt.h @@ -45,7 +45,7 @@ extern "C" { /* The max key length of all supported algorithms */ #define MY_AES_MAX_KEY_LENGTH 32 -#define MY_AES_CTX_SIZE 672 +#define MY_AES_CTX_SIZE 1040 enum my_aes_mode { MY_AES_ECB, MY_AES_CBC diff --git a/libmysqld/lib_sql.cc b/libmysqld/lib_sql.cc index bbbe10121ba..d4edd24291b 100644 --- a/libmysqld/lib_sql.cc +++ b/libmysqld/lib_sql.cc @@ -1057,7 +1057,7 @@ class Client_field_extension: public Sql_alloc, public: Client_field_extension() { - memset(this, 0, sizeof(*this)); + memset((void*) this, 0, sizeof(*this)); } void copy_extended_metadata(MEM_ROOT *memroot, const Send_field_extended_metadata &src) diff --git a/mysql-test/include/have_innodb.inc b/mysql-test/include/have_innodb.inc index 0de070e1994..8c9cdb54363 100644 --- a/mysql-test/include/have_innodb.inc +++ b/mysql-test/include/have_innodb.inc @@ -3,7 +3,7 @@ # will be skipped unless innodb is enabled # --disable_query_log -if (`select count(*) from information_schema.system_variables where variable_name='have_sanitizer' and global_value like "MSAN%"`) +if (`select count(*) from information_schema.system_variables where variable_name='have_sanitizer' and global_value like 'MSAN%'`) { SET STATEMENT sql_log_bin=0 FOR call mtr.add_suppression("InnoDB: Trying to delete tablespace.*pending operations"); diff --git a/mysql-test/include/have_innodb_16k.opt b/mysql-test/include/have_innodb_16k.opt new file mode 100644 index 00000000000..2ece0f02d02 --- /dev/null +++ b/mysql-test/include/have_innodb_16k.opt @@ -0,0 +1 @@ +--innodb-page-size=16k diff --git a/mysql-test/include/have_innodb_32k.opt b/mysql-test/include/have_innodb_32k.opt new file mode 100644 index 00000000000..cabc8fc7378 --- /dev/null +++ b/mysql-test/include/have_innodb_32k.opt @@ -0,0 +1 @@ +--innodb-page-size=32k diff --git a/mysql-test/include/have_innodb_4k.opt b/mysql-test/include/have_innodb_4k.opt new file mode 100644 index 00000000000..e5b58602036 --- /dev/null +++ b/mysql-test/include/have_innodb_4k.opt @@ -0,0 +1 @@ +--innodb-page-size=4k diff --git a/mysql-test/include/have_innodb_64k.opt b/mysql-test/include/have_innodb_64k.opt new file mode 100644 index 00000000000..c70123809fc --- /dev/null +++ b/mysql-test/include/have_innodb_64k.opt @@ -0,0 +1 @@ +--innodb-page-size=64k diff --git a/mysql-test/include/have_innodb_8k.opt b/mysql-test/include/have_innodb_8k.opt new file mode 100644 index 00000000000..f75efe9af79 --- /dev/null +++ b/mysql-test/include/have_innodb_8k.opt @@ -0,0 +1 @@ +--innodb-page-size=8k diff --git a/mysql-test/include/have_normal_bzip.inc b/mysql-test/include/have_normal_bzip.inc new file mode 100644 index 00000000000..36c06274398 --- /dev/null +++ b/mysql-test/include/have_normal_bzip.inc @@ -0,0 +1,9 @@ +--source include/have_compress.inc + +# Test that the system is using the default/standard bzip library. +# If not, we have to skip the test as the compression lengths displayed +# in the test will not match the results from used compression library. + +if (`select length(COMPRESS(space(5000))) != 33`) { + skip Test skipped as standard bzip is needed; +} diff --git a/mysql-test/include/linux.inc b/mysql-test/include/linux.inc index f24832ca476..cc126ff1d73 100644 --- a/mysql-test/include/linux.inc +++ b/mysql-test/include/linux.inc @@ -1,4 +1,4 @@ -if (`select convert(@@version_compile_os using latin1) LIKE 'Linux' = 0`) +if (`select @@version_compile_os not LIKE 'Linux%'`) { skip Need Linux; } diff --git a/mysql-test/include/rpl_change_topology.inc b/mysql-test/include/rpl_change_topology.inc index 387ab196ad1..b63700b059b 100644 --- a/mysql-test/include/rpl_change_topology.inc +++ b/mysql-test/include/rpl_change_topology.inc @@ -5,15 +5,15 @@ # need to change topology after they have sourced include/rpl_init.inc # # This file sets up variables needed by include/rpl_sync.inc and many -# other replication scripts in the include/ directory. It also issues +# other replication scripts in the include/ directory. It also issues # CHANGE MASTER on all servers where the configuration changes from -# what it was before. It does not issue START SLAVE (use +# what it was before. It does not issue START SLAVE (use # include/rpl_start_slaves.inc for that). # # Note: it is not currently possible to change the number of servers # after the rpl_init.inc, without first calling rpl_end.inc. So the # test has to set $rpl_server_count to the total number of servers -# that the test uses, before it sources include/rpl_init.inc. After +# that the test uses, before it sources include/rpl_init.inc. After # that, $rpl_server_count must not change until after next time the # test sources include/rpl_end.inc. # @@ -37,7 +37,7 @@ # By default, CHANGE MASTER is executed with MASTER_LOG_FILE set # to the name of the last binlog file on the master (retrieved by # executing SHOW MASTER STATUS). This variable can be set to -# specify another filename. This variable should be a +# specify another filename. This variable should be a # comma-separated list of the following form: # # SERVER_NUMBER_1:FILE_NAME_1,SERVER_NUMBER_2:FILE_NAME_2,... @@ -45,7 +45,7 @@ # Before CHANGE MASTER is executed on server N, this script checks # if $rpl_master_log_file contains the text N:FILE_NAME. If it # does, then MASTER_LOG_FILE is set to FILE_NAME. Otherwise, -# MASTER_LOG_FILE is set to the last binlog on the master. For +# MASTER_LOG_FILE is set to the last binlog on the master. For # example, to specify that server_1 should start replicate from # master-bin.000007 and server_5 should start replicate from # master-bin.012345, do: @@ -53,9 +53,9 @@ # # $rpl_master_log_pos # By default, CHANGE MASTER is executed without specifying the -# MASTER_LOG_POS parameter. This variable can be set to set a -# specific position. It has the same form as $rpl_master_log_file -# (see above). For example, to specify that server_3 should start +# MASTER_LOG_POS parameter. This variable can be set to set a +# specific position. It has the same form as $rpl_master_log_file +# (see above). For example, to specify that server_3 should start # replicate from position 4711 of its master, do: # --let $rpl_master_log_pos= 3:4711 # @@ -72,7 +72,7 @@ # include/rpl_stop_slaves.inc # include/rpl_end.inc # -# $rpl_server_count_length: +# $rpl_server_count_length # Set to LENGTH($rpl_server_count). So if $rpl_server_count < 10, # then $rpl_server_count_length = 1; if 10 <= $rpl_server_count < # 100, then $rpl_server_count_length = 2, etc. @@ -83,12 +83,12 @@ # server N is a slave, then the N'th number is the master of server # N. If server N is not a slave, then the N'th number is just spaces # (so in fact it is not a number). For example, if $rpl_topology is -# '1->2,2->3,3->1,2->4,5->6', then $rpl_master_list is '3122 6'. +# '1->2,2->3,3->1,2->4,5->6', then $rpl_master_list is '3122 5'. # # $rpl_sync_chain_dirty -# This variable is set to 1. This tells include/rpl_sync.inc to +# This variable is set to 1. This tells include/rpl_sync.inc to # compute a new value for $rpl_sync_chain next time that -# include/rpl_sync.inc is sourced. See +# include/rpl_sync.inc is sourced. See # include/rpl_generate_sync_chain.inc and include/rpl_sync.inc for # details. @@ -124,7 +124,7 @@ if ($rpl_master_list == '') if ($rpl_debug) { --echo \$rpl_server_count='$rpl_server_count' - --echo \$rpl_server_count_length='$rpl_server_count_length' + --echo old \$rpl_server_count_length='$rpl_server_count_length' --echo new \$rpl_topology='$_rpl_topology' --echo old \$rpl_master_list='$rpl_master_list' --echo old \$rpl_sync_chain='$rpl_sync_chain' @@ -210,6 +210,10 @@ if (!$rpl_skip_change_master) --let $rpl_connection_name= server_$_rpl_master --source include/rpl_connection.inc --let $_rpl_master_log_file= query_get_value(SHOW MASTER STATUS, File, 1) + if ($rpl_debug) + { + --echo "\$rpl_master_log_file parameter not set for the master: $_rpl_master, use the latest binlog file by executing SHOW MASTER STATUS." + } } # Change connection. --let $rpl_connection_name= server_$_rpl_server @@ -224,6 +228,10 @@ if (!$rpl_skip_change_master) if (!$_rpl_master_log_pos_index) { --let $_rpl_master_log_pos= + if ($rpl_debug) + { + --echo "\$rpl_master_log_pos parameter not set for the master: $_rpl_master. Set log position to empty." + } } if ($rpl_master_log_file) { diff --git a/mysql-test/include/rpl_connect.inc b/mysql-test/include/rpl_connect.inc index e30769eb335..a962ba6f601 100644 --- a/mysql-test/include/rpl_connect.inc +++ b/mysql-test/include/rpl_connect.inc @@ -5,7 +5,7 @@ # This script is normally used internally by rpl_init.inc and # master-slave.inc, but it can also be used in test cases that need to # create more connections or re-create connections after disconnect. -# +# Default ports SERVER_MYPORT_[1,2] are set by rpl_init.inc. # # ==== Usage ==== # diff --git a/mysql-test/include/rpl_end.inc b/mysql-test/include/rpl_end.inc index f49079db332..02564a92580 100644 --- a/mysql-test/include/rpl_end.inc +++ b/mysql-test/include/rpl_end.inc @@ -103,11 +103,9 @@ while ($_rpl_server) --connection default --let $_rpl_server= $rpl_server_count ---let $_rpl_one= _1 while ($_rpl_server) { --disconnect server_$_rpl_server - --disconnect server_$_rpl_server$_rpl_one --dec $_rpl_server } diff --git a/mysql-test/include/rpl_for_each_slave.inc b/mysql-test/include/rpl_for_each_slave.inc index 65d242cf894..c1d4581dfa5 100644 --- a/mysql-test/include/rpl_for_each_slave.inc +++ b/mysql-test/include/rpl_for_each_slave.inc @@ -1,7 +1,7 @@ # ==== Purpose ==== # # Execute a .inc file once for each server that was configured as a -# slave by rpl_init.inc +# slave by rpl_init.inc, for example start_slave.inc or stop_slave.inc file. # # # ==== Usage ==== @@ -14,6 +14,20 @@ # $rpl_source_file # The file that will be sourced. # +# $rpl_server_count +# The number of servers to configure. If this is not set, the largest +# number in $rpl_topology will be used. +# This parameter is obtained from rpl_init.inc. +# +# $rpl_master_list +# This parameter is calculated from within rpl_init.inc. +# +# $rpl_server_count_length +# Set to LENGTH($rpl_server_count). So if $rpl_server_count < 10, +# then $rpl_server_count_length = 1; if 10 <= $rpl_server_count < +# 100, then $rpl_server_count_length = 2, etc. +# This parameter is calculated from within rpl_change_topology.inc. +# # $rpl_debug # See include/rpl_init.inc diff --git a/mysql-test/include/rpl_init.inc b/mysql-test/include/rpl_init.inc index acb9104ae6f..26ce4e1b57f 100644 --- a/mysql-test/include/rpl_init.inc +++ b/mysql-test/include/rpl_init.inc @@ -3,18 +3,16 @@ # Set up replication on several servers in a specified topology. # # By default, this script does the following: -# - Creates the connections server_1, server_2, ..., server_N, as -# well as extra connections server_1_1, server_2_1, ..., -# server_N_1. server_I and server_I_1 are connections to the same -# server. -# - Verifies that @@server_id of all servers are different. +# - Creates the connections server_1, server_2, ..., server_N. # - Calls RESET MASTER, RESET SLAVE, USE test, CHANGE MASTER, START SLAVE. # - Sets the connection to server_1 before exiting. +# With $rpl_check_server_ids parameter, the script does the following: +# - Verifies that @@server_id of all servers are different. # # ==== Usage ==== # # 1. If you are going to use more than two servers, create -# rpl_test.cfg with the following contents: +# rpl_test.cnf with the following contents: # # !include ../my.cnf # [mysqld.1] @@ -34,8 +32,9 @@ # # (It is allowed, but not required, to configure SERVER_MYPORT_1 # and SERVER_MYPORT_2 too. If these variables are not set, the -# variables MASTER_MYPORT and SLAVE_MYPORT, configured in the -# default my.cnf used by the rpl suite, are used instead.) +# variables MASTER_MYPORT and SLAVE_MYPORT are used instead. +# These variables are configured in the rpl_1slave_base.cnf, +# that is used in the default my.cnf, which is used by the rpl suite.) # # 2. Execute the following near the top of the test: # @@ -147,18 +146,15 @@ if (!$rpl_debug) } -# Create two connections to each server; reset master/slave, select +# Create connection to the server; reset master/slave, select # database, set autoinc variables. --let $_rpl_server= $rpl_server_count ---let $_rpl_one= _1 while ($_rpl_server) { # Connect. --let $rpl_server_number= $_rpl_server --let $rpl_connection_name= server_$_rpl_server --source include/rpl_connect.inc - --let $rpl_connection_name= server_$_rpl_server$_rpl_one - --source include/rpl_connect.inc # Configure server. --let $rpl_connection_name= server_$_rpl_server @@ -203,7 +199,7 @@ if ($rpl_check_server_ids) while ($_rpl_server2) { --let $assert_text= Servers $_rpl_server and $_rpl_server2 should have different @@server_id - --let $assert_condition= [$_rpl_server:SELECT @@server_id AS i, i, 1] != [$_rpl_server2:SELECT @@server_id AS i, i, 1] + --let $assert_cond= [SELECT @@server_id AS i, i, 1] != $_rpl_server --source include/assert.inc --dec $_rpl_server2 @@ -212,18 +208,30 @@ if ($rpl_check_server_ids) } } -# $rpl_master_list must be set so that include/rpl_change_topology.inc -# knows which servers are initialized and not. +if ($rpl_debug) +{ + --echo ---- Check the topology and call CHANGE MASTER ---- +} + +# $rpl_master_list must be set so that include/rpl_change_topology.inc and later +# include/rpl_for_each_slave.inc knows which servers are initialized and not. --let $rpl_master_list= `SELECT REPEAT('x', $rpl_server_count * LENGTH($rpl_server_count))` --source include/rpl_change_topology.inc if (!$rpl_skip_start_slave) { + if ($rpl_debug) + { + --echo ---- Start slaves ---- + } --source include/rpl_start_slaves.inc } - +if ($rpl_debug) +{ + --echo ---- Set connection to the server_1 ---- +} --let $rpl_connection_name= server_1 --source include/rpl_connection.inc diff --git a/mysql-test/include/rpl_reconnect.inc b/mysql-test/include/rpl_reconnect.inc index cdbbd0a1bf1..9438c774461 100644 --- a/mysql-test/include/rpl_reconnect.inc +++ b/mysql-test/include/rpl_reconnect.inc @@ -72,11 +72,6 @@ if (!$_rpl_server_number) --source include/rpl_connection.inc --enable_reconnect ---let $_rpl_one= _1 ---let $rpl_connection_name= server_$rpl_server_number$_rpl_one ---source include/rpl_connection.inc ---enable_reconnect - if ($rpl_debug) { --echo ---- Wait for reconnect and disable reconnect on all connections ---- @@ -122,11 +117,5 @@ if (!$_rpl_server_number) --source include/wait_until_connected_again.inc --disable_reconnect ---let $rpl_connection_name= server_$rpl_server_number$_rpl_one ---source include/rpl_connection.inc ---source include/wait_until_connected_again.inc ---disable_reconnect - - --let $include_filename= rpl_reconnect.inc --source include/end_include_file.inc diff --git a/mysql-test/include/rpl_start_slaves.inc b/mysql-test/include/rpl_start_slaves.inc index fdd90eb12c5..9c1f9f7b293 100644 --- a/mysql-test/include/rpl_start_slaves.inc +++ b/mysql-test/include/rpl_start_slaves.inc @@ -19,7 +19,7 @@ # # $slave_timeout # Set the timeout when waiting for slave threads to stop and -# start, respectively. See include/wait_for_slave_param.inc +# start, respectively. See include/wait_for_slave_param.inc --let $include_filename= rpl_start_slaves.inc diff --git a/mysql-test/include/wait_for_slave_io_to_start.inc b/mysql-test/include/wait_for_slave_io_to_start.inc index cd8e5d374a4..0cb4091755c 100644 --- a/mysql-test/include/wait_for_slave_io_to_start.inc +++ b/mysql-test/include/wait_for_slave_io_to_start.inc @@ -14,13 +14,14 @@ # # Parameters: # $slave_timeout -# See include/wait_for_slave_param.inc +# Timeout used when waiting for the slave IO thread to start. +# See include/wait_for_slave_param.inc. # # $rpl_allow_error # By default, this file fails if there is an error in the IO -# thread. However, the IO thread can recover and reconnect after -# certain errors. If such an error is expected, can set -# $rpl_allow_error=1. This will prevent this file from failing if +# thread. However, the IO thread can recover and reconnect after +# certain errors. If such an error is expected, can set +# $rpl_allow_error=1. This will prevent this file from failing if # there is an error in the IO thread. # # $rpl_debug diff --git a/mysql-test/include/wait_for_slave_sql_to_start.inc b/mysql-test/include/wait_for_slave_sql_to_start.inc index 4aea9fba569..9286f1a08a2 100644 --- a/mysql-test/include/wait_for_slave_sql_to_start.inc +++ b/mysql-test/include/wait_for_slave_sql_to_start.inc @@ -11,6 +11,7 @@ # # Parameters: # $slave_timeout +# Timeout used when waiting for the slave SQL thread to start. # See include/wait_for_slave_param.inc # # $rpl_debug @@ -25,7 +26,7 @@ let $slave_param= Slave_SQL_Running; let $slave_param_value= Yes; # Unfortunately, the slave sql thread sets Slave_SQL_Running=Yes -# *before* it clears Last_SQL_Errno. So we have to allow errors in +# *before* it clears Last_SQL_Errno. So we have to allow errors in # the SQL thread here. #--let $slave_error_param= Last_SQL_Errno diff --git a/mysql-test/include/wait_for_slave_to_start.inc b/mysql-test/include/wait_for_slave_to_start.inc index a916e2ea615..742e7f7e0b4 100644 --- a/mysql-test/include/wait_for_slave_to_start.inc +++ b/mysql-test/include/wait_for_slave_to_start.inc @@ -12,6 +12,7 @@ # # Parameters: # $slave_timeout +# Timeout used when waiting for the slave threads to start. # See include/wait_for_slave_param.inc # # $rpl_debug diff --git a/mysql-test/lib/My/Debugger.pm b/mysql-test/lib/My/Debugger.pm index 376325cf644..b068698e340 100644 --- a/mysql-test/lib/My/Debugger.pm +++ b/mysql-test/lib/My/Debugger.pm @@ -94,7 +94,7 @@ py import subprocess,shlex,time valg=subprocess.Popen(shlex.split("""valgrind --tool=memcheck --show-reachable=yes --leak-check=yes --num-callers=16 --quiet --suppressions=valgrind.supp --vgdb-error=0 {exe} {args} --loose-wait-for-pos-timeout=1500""")) time.sleep(2) -gdb.execute("target remote | /usr/lib64/valgrind/../../bin/vgdb --pid=" + str(valg.pid)) +gdb.execute("target remote | vgdb --pid=" + str(valg.pid)) EEE pre => sub { my $debug_libraries_path= "/usr/lib/debug"; diff --git a/mysql-test/lib/My/Platform.pm b/mysql-test/lib/My/Platform.pm index b8bc9f8ec84..2b32ef87b81 100644 --- a/mysql-test/lib/My/Platform.pm +++ b/mysql-test/lib/My/Platform.pm @@ -20,9 +20,10 @@ package My::Platform; use strict; use File::Basename; use File::Path; +use Carp; use base qw(Exporter); -our @EXPORT= qw(IS_CYGWIN IS_WINDOWS IS_WIN32PERL IS_AIX +our @EXPORT= qw(IS_CYGWIN IS_MSYS IS_WINDOWS IS_WIN32PERL IS_AIX native_path posix_path mixed_path check_socket_path_length process_alive open_for_append); @@ -33,9 +34,15 @@ BEGIN { die "Could not execute 'cygpath': $!"; } eval 'sub IS_CYGWIN { 1 }'; + eval 'sub IS_MSYS { 0 }'; + } + elsif ($^O eq "msys") { + eval 'sub IS_CYGWIN { 1 }'; + eval 'sub IS_MSYS { 1 }'; } else { eval 'sub IS_CYGWIN { 0 }'; + eval 'sub IS_MSYS { 0 }'; } if ($^O eq "MSWin32") { eval 'sub IS_WIN32PERL { 1 }'; @@ -95,8 +102,13 @@ sub mixed_path { sub native_path { my ($path)= @_; - $path=~ s/\//\\/g - if (IS_CYGWIN or IS_WIN32PERL); + if (IS_CYGWIN) { + # \\\\ protects against 2 expansions (just for the case) + $path=~ s/\/+|\\+/\\\\\\\\/g; + } + elsif (IS_WINDOWS) { + $path=~ s/\/+/\\/g; + } return $path; } @@ -219,4 +231,69 @@ sub open_for_append } +sub check_cygwin_subshell +{ + # Only pipe (or sh-expansion) is fed to /bin/sh + my $out= `echo %comspec%|cat`; + return ($out =~ /\bcmd.exe\b/) ? 0 : 1; +} + +sub install_shell_wrapper() +{ + system("rm -f /bin/sh.exe") and die $!; + my $wrapper= <<'EOF'; +#!/bin/bash +if [[ -n "$MTR_PERL" && "$1" = "-c" ]]; then + shift + exec $(cygpath -m "$COMSPEC") /C "$@" +fi +exec /bin/bash "$@" +EOF + open(OUT, '>', "/bin/sh") or die "/bin/sh: $!\n"; + print OUT $wrapper; + close(OUT); + system("chmod +x /bin/sh") and die $!; + print "Cygwin subshell wrapper /bin/sh was installed, please restart MTR!\n"; + exit(0); +} + +sub uninstall_shell_wrapper() +{ + system("rm -f /bin/sh") and die $!; + system("cp /bin/bash.exe /bin/sh.exe") and die $!; +} + +sub cygwin_subshell_fix +{ + my ($opt_name, $opt_value)= @_; + if ($opt_name ne "cygwin-subshell-fix") { + confess "Wrong option name: ${opt_name}"; + } + if ($opt_value eq "do") { + if (check_cygwin_subshell()) { + install_shell_wrapper(); + } else { + print "Cygwin subshell fix was already installed, skipping...\n"; + } + } elsif ($opt_value eq "remove") { + if (check_cygwin_subshell()) { + print "Cygwin subshell fix was already uninstalled, skipping...\n"; + } else { + uninstall_shell_wrapper(); + } + } else { + die "Wrong --cygwin-subshell-fix value: ${opt_value} (expected do/remove)"; + } +} + +sub options +{ + if (IS_CYGWIN) { + return ('cygwin-subshell-fix=s' => \&cygwin_subshell_fix); + } else { + return (); + } +} + + 1; diff --git a/mysql-test/lib/My/SafeProcess.pm b/mysql-test/lib/My/SafeProcess.pm index 69033649b46..e3b46b3709e 100644 --- a/mysql-test/lib/My/SafeProcess.pm +++ b/mysql-test/lib/My/SafeProcess.pm @@ -102,7 +102,7 @@ else # Find the safe process binary or script sub find_bin { - if (IS_WIN32PERL or IS_CYGWIN) + if (IS_WINDOWS) { # Use my_safe_process.exe my $exe= my_find_bin($bindir, ["lib/My/SafeProcess", "My/SafeProcess"], diff --git a/mysql-test/lib/My/Test.pm b/mysql-test/lib/My/Test.pm index 49ce2fb5af9..56e7cf6d8a4 100644 --- a/mysql-test/lib/My/Test.pm +++ b/mysql-test/lib/My/Test.pm @@ -111,7 +111,7 @@ sub read_test { $serialized =~ s/\\([0-9a-fA-F]{2})/chr(hex($1))/eg; my $test= Storable::thaw($serialized); use Data::Dumper; - die "wrong class (hack attempt?): ".ref($test)."\n".Dumper(\$test, $serialized) + confess "Not My::Test: ". ref($test). "\n". Dumper(\$test, $serialized) unless ref($test) eq 'My::Test'; resfile_from_test($test) if $::opt_resfile; return $test; diff --git a/mysql-test/lib/mtr_report.pm b/mysql-test/lib/mtr_report.pm index 2a8ed65eb2c..7d944ade71a 100644 --- a/mysql-test/lib/mtr_report.pm +++ b/mysql-test/lib/mtr_report.pm @@ -48,6 +48,7 @@ our $timestamp= 0; our $timediff= 0; our $name; our $verbose; +# TODO: no option for that? Why is it different from $verbose? our $verbose_restart= 0; our $timer= 1; our $tests_total; diff --git a/mysql-test/main/alter_table.result b/mysql-test/main/alter_table.result index 6904f76ff88..fe53977b160 100644 --- a/mysql-test/main/alter_table.result +++ b/mysql-test/main/alter_table.result @@ -3068,6 +3068,40 @@ drop table t1; # End of 10.5 tests # # +# MDEV-32449 Server crashes in Alter_info::add_stat_drop_index upon CREATE TABLE +# +CREATE TABLE t1 ( +`altcol1` blob DEFAULT '', +KEY `altcol1` (`altcol1`(2300)) +) ROW_FORMAT=PAGE, ENGINE=Aria; +ALTER TABLE t1 ADD FOREIGN KEY h (`altcol1`) REFERENCES t1 (`altcol1`) ON UPDATE SET DEFAULT, ALGORITHM=COPY; +Warnings: +Note 1071 Specified key was too long; max key length is 2300 bytes +create or replace table t2 like t1; +show create table t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `altcol1` blob DEFAULT '', + KEY `altcol1` (`altcol1`(2300)), + KEY `h` (`altcol1`(2300)) +) ENGINE=Aria DEFAULT CHARSET=latin1 COLLATE=latin1_swedish_ci PAGE_CHECKSUM=1 ROW_FORMAT=PAGE +show create table t2; +Table Create Table +t2 CREATE TABLE `t2` ( + `altcol1` blob DEFAULT '', + KEY `altcol1` (`altcol1`(2300)) +) ENGINE=Aria DEFAULT CHARSET=latin1 COLLATE=latin1_swedish_ci PAGE_CHECKSUM=1 ROW_FORMAT=PAGE +drop table t1,t2; +# Another test for MDEV-32449 +CREATE TABLE t1 (a POINT, b POINT, KEY(a)) ENGINE=Aria; +ALTER TABLE t1 ADD FOREIGN KEY (a) REFERENCES t (b); +CREATE TEMPORARY TABLE t2 LIKE t1; +DROP TEMPORARY TABLE t2; +DROP TABLE t1; +# +# End of 10.6 tests +# +# # MDEV-26767 Server crashes when rename table and alter storage engine # alter table txxx engine=innodb, rename to tyyy; diff --git a/mysql-test/main/alter_table.test b/mysql-test/main/alter_table.test index 8cf71b0def7..e2a3b2866f1 100644 --- a/mysql-test/main/alter_table.test +++ b/mysql-test/main/alter_table.test @@ -2375,6 +2375,32 @@ drop table t1; --echo # End of 10.5 tests --echo # +--echo # +--echo # MDEV-32449 Server crashes in Alter_info::add_stat_drop_index upon CREATE TABLE +--echo # + +CREATE TABLE t1 ( + `altcol1` blob DEFAULT '', + KEY `altcol1` (`altcol1`(2300)) +) ROW_FORMAT=PAGE, ENGINE=Aria; +ALTER TABLE t1 ADD FOREIGN KEY h (`altcol1`) REFERENCES t1 (`altcol1`) ON UPDATE SET DEFAULT, ALGORITHM=COPY; +create or replace table t2 like t1; +show create table t1; +show create table t2; +drop table t1,t2; + +--echo # Another test for MDEV-32449 + +CREATE TABLE t1 (a POINT, b POINT, KEY(a)) ENGINE=Aria; +ALTER TABLE t1 ADD FOREIGN KEY (a) REFERENCES t (b); +CREATE TEMPORARY TABLE t2 LIKE t1; +DROP TEMPORARY TABLE t2; +DROP TABLE t1; + +--echo # +--echo # End of 10.6 tests +--echo # + --echo # --echo # MDEV-26767 Server crashes when rename table and alter storage engine --echo # diff --git a/mysql-test/main/analyze.result b/mysql-test/main/analyze.result index a1332abd177..aac9ed7b3a2 100644 --- a/mysql-test/main/analyze.result +++ b/mysql-test/main/analyze.result @@ -71,3 +71,351 @@ optimize table t1 extended; ERROR 42000: You have an error in your SQL syntax; check the manual that corresponds to your MariaDB server version for the right syntax to use near 'extended' at line 1 drop table t1; End of 5.0 tests +# +# Test analyze of text column (not yet supported) +# +set optimizer_use_condition_selectivity=4; +set histogram_type='single_prec_hb'; +set histogram_size=255; +create table t1 (a int not null, t tinytext, tx text); +insert into t1 select seq+1, repeat('X',seq*5), repeat('X',seq*10) from seq_0_to_50; +insert into t1 select seq+100, repeat('X',5), "" from seq_1_to_10; +analyze table t1; +Table Op Msg_type Msg_text +test.t1 analyze status Engine-independent statistics collected +test.t1 analyze Warning Engine-independent statistics are not collected for column 't' +test.t1 analyze Warning Engine-independent statistics are not collected for column 'tx' +test.t1 analyze status OK +explain select count(*) from t1 where t='XXXXXX'; +id select_type table type possible_keys key key_len ref rows Extra +1 SIMPLE t1 ALL NULL NULL NULL NULL 61 Using where +select column_name, min_value, max_value, hist_size from mysql.column_stats where table_name='t1'; +column_name min_value max_value hist_size +a 1 110 255 +drop table t1; +set use_stat_tables=default; +set histogram_type=default; +set histogram_size=default; +# +# MDEV-31957 Concurrent ALTER and ANALYZE collecting statistics can +# result in stale statistical data +# +CREATE TABLE t1 (a INT, b VARCHAR(128)); +INSERT INTO t1 SELECT seq, CONCAT('s',seq) FROM seq_1_to_100; +connect con1,localhost,root,,; +ALTER TABLE t1 MODIFY b BLOB; +connection default; +ANALYZE TABLE t1 PERSISTENT FOR ALL; +connection con1; +ANALYZE TABLE t1 PERSISTENT FOR ALL; +connection default; +disconnect con1; +select db_name,table_name,column_name from mysql.column_stats; +db_name table_name column_name +test t1 a +drop table t1; +# +# Testing swapping columns +# +create or replace table t1 (a int primary key, b varchar(100), c varchar(100), d varchar(100)) engine=innodb; +insert into t1 select seq, repeat('b',seq),repeat('c',mod(seq,5)), repeat('d',mod(seq,10)) from seq_1_to_100; +ANALYZE TABLE t1 PERSISTENT FOR ALL; +Table Op Msg_type Msg_text +test.t1 analyze status Engine-independent statistics collected +test.t1 analyze status OK +select db_name,table_name,column_name,avg_length from mysql.column_stats order by column_name; +db_name table_name column_name avg_length +test t1 a 4.0000 +test t1 b 50.5000 +test t1 c 2.0000 +test t1 d 4.5000 +alter table t1 change b c varchar(200), change c b varchar(200); +select db_name,table_name,column_name,avg_length from mysql.column_stats order by column_name; +db_name table_name column_name avg_length +test t1 a 4.0000 +test t1 b 2.0000 +test t1 c 50.5000 +test t1 d 4.5000 +alter table t1 change b c varchar(200), change c d varchar(200), change d b varchar(200) ; +select db_name,table_name,column_name,avg_length from mysql.column_stats order by column_name; +db_name table_name column_name avg_length +test t1 a 4.0000 +test t1 b 4.5000 +test t1 c 2.0000 +test t1 d 50.5000 +alter table t1 change b c varchar(200), change c d varchar(200), change d e varchar(200) ; +select db_name,table_name,column_name,avg_length from mysql.column_stats order by column_name; +db_name table_name column_name avg_length +test t1 a 4.0000 +test t1 c 4.5000 +test t1 d 2.0000 +test t1 e 50.5000 +alter table t1 change e d varchar(200), drop column d; +select db_name,table_name,column_name,avg_length from mysql.column_stats order by column_name; +db_name table_name column_name avg_length +test t1 a 4.0000 +test t1 c 4.5000 +test t1 d 50.5000 +# Test having non existing column in column_stats +insert into mysql.column_stats (db_name,table_name,column_name) values ("test","t1","b"); +alter table t1 change c d varchar(200), change d b varchar(200); +select db_name,table_name,column_name,avg_length from mysql.column_stats order by column_name; +db_name table_name column_name avg_length +test t1 a 4.0000 +test t1 b 50.5000 +test t1 d 4.5000 +# Test having a conflicting temporary name +insert into mysql.column_stats (db_name,table_name,column_name) values ("test","t1",concat("#sql_tmp_name#1",char(0))); +alter table t1 change d b varchar(200), change b d varchar(200); +select db_name,table_name,column_name,avg_length from mysql.column_stats order by column_name; +db_name table_name column_name avg_length +test t1 a 4.0000 +test t1 b 4.5000 +test t1 d 50.5000 +drop table t1; +truncate table mysql.column_stats; +create or replace table t1 (a int primary key, b varchar(100), c varchar(100), d varchar(100)) engine=myisam; +insert into t1 select seq, repeat('b',seq),repeat('c',mod(seq,5)), repeat('d',mod(seq,10)) from seq_1_to_100; +ANALYZE TABLE t1 PERSISTENT FOR ALL; +Table Op Msg_type Msg_text +test.t1 analyze status Engine-independent statistics collected +test.t1 analyze status OK +select db_name,table_name,column_name,avg_length from mysql.column_stats order by column_name; +db_name table_name column_name avg_length +test t1 a 4.0000 +test t1 b 50.5000 +test t1 c 2.0000 +test t1 d 4.5000 +alter table t1 change b c varchar(200), change c b varchar(200); +select db_name,table_name,column_name,avg_length from mysql.column_stats order by column_name; +db_name table_name column_name avg_length +test t1 a 4.0000 +test t1 d 4.5000 +analyze table t1 persistent for columns(b,c) indexes all; +Table Op Msg_type Msg_text +test.t1 analyze status Engine-independent statistics collected +test.t1 analyze status Table is already up to date +alter table t1 change b c varchar(200), change c d varchar(200), change d b varchar(200) ; +select db_name,table_name,column_name,avg_length from mysql.column_stats order by column_name; +db_name table_name column_name avg_length +test t1 a 4.0000 +test t1 b 50.5000 +test t1 c 2.0000 +analyze table t1 persistent for columns(d) indexes all; +Table Op Msg_type Msg_text +test.t1 analyze status Engine-independent statistics collected +test.t1 analyze status Table is already up to date +alter table t1 change b c varchar(200), change c d varchar(200), change d e varchar(200) ; +select db_name,table_name,column_name,avg_length from mysql.column_stats order by column_name; +db_name table_name column_name avg_length +test t1 a 4.0000 +test t1 c 50.5000 +test t1 d 2.0000 +test t1 e 50.5000 +alter table t1 change e d varchar(200), drop column d; +select db_name,table_name,column_name,avg_length from mysql.column_stats order by column_name; +db_name table_name column_name avg_length +test t1 a 4.0000 +test t1 c 50.5000 +test t1 d 50.5000 +drop table t1; +truncate table mysql.column_stats; +create table t1 (a int, b blob, unique(b)) engine= innodb; +analyze table t1 persistent for all; +Table Op Msg_type Msg_text +test.t1 analyze status Engine-independent statistics collected +test.t1 analyze Warning Engine-independent statistics are not collected for column 'b' +test.t1 analyze status OK +select column_name from mysql.column_stats where table_name = 't1'; +column_name +a +drop table t1; +create table t1 (a int, b blob, c int generated always as (length(b)) virtual) engine= innodb; +analyze table t1 persistent for all; +Table Op Msg_type Msg_text +test.t1 analyze status Engine-independent statistics collected +test.t1 analyze Warning Engine-independent statistics are not collected for column 'b' +test.t1 analyze status OK +select column_name from mysql.column_stats where table_name = 't1'; +column_name +a +c +drop table t1; +CREATE or replace TABLE t1 (a INT, b CHAR(8)); +ANALYZE TABLE t1 PERSISTENT FOR ALL; +Table Op Msg_type Msg_text +test.t1 analyze status Engine-independent statistics collected +test.t1 analyze status Table is already up to date +ALTER TABLE t1 CHANGE b c INT, ORDER BY b; +SELECT db_name, table_name, column_name FROM mysql.column_stats where table_name = 't1'; +db_name table_name column_name +test t1 a +test t1 c +drop table t1; +CREATE or replace TABLE t1 (a INT, b CHAR(8)); +ANALYZE TABLE t1 PERSISTENT FOR ALL; +Table Op Msg_type Msg_text +test.t1 analyze status Engine-independent statistics collected +test.t1 analyze status Table is already up to date +ALTER TABLE t1 RENAME COLUMN b to c, ALGORITHM=COPY; +SELECT db_name, table_name, column_name FROM mysql.column_stats where table_name = 't1'; +db_name table_name column_name +test t1 a +test t1 c +drop table t1; +# +# Testing swapping indexes +# +create or replace table t1 (a int primary key, b varchar(100), c varchar(100), d varchar(100), index (b), index(c), index(d,b)) engine=innodb; +insert into t1 select seq, repeat('b',seq),repeat('c',mod(seq,5)), repeat('d',mod(seq,10)) from seq_1_to_100; +ANALYZE TABLE t1 PERSISTENT FOR ALL; +Table Op Msg_type Msg_text +test.t1 analyze status Engine-independent statistics collected +test.t1 analyze status OK +select * from mysql.index_stats order by index_name, prefix_arity; +db_name table_name index_name prefix_arity avg_frequency +test t1 PRIMARY 1 1.0000 +test t1 b 1 1.0000 +test t1 b 2 1.0000 +test t1 c 1 20.0000 +test t1 c 2 1.0000 +test t1 d 1 10.0000 +test t1 d 2 1.0000 +test t1 d 3 1.0000 +alter table t1 rename index b to c, rename index c to d, rename index d to b; +select * from mysql.index_stats order by index_name; +db_name table_name index_name prefix_arity avg_frequency +test t1 PRIMARY 1 1.0000 +test t1 b 1 10.0000 +test t1 b 2 1.0000 +test t1 b 3 1.0000 +test t1 c 1 1.0000 +test t1 c 2 1.0000 +test t1 d 1 20.0000 +test t1 d 2 1.0000 +alter table t1 rename index b to c, rename index c to d, rename index d to e; +select * from mysql.index_stats order by index_name, prefix_arity; +db_name table_name index_name prefix_arity avg_frequency +test t1 PRIMARY 1 1.0000 +test t1 c 1 10.0000 +test t1 c 2 1.0000 +test t1 c 3 1.0000 +test t1 d 1 1.0000 +test t1 d 2 1.0000 +test t1 e 1 20.0000 +test t1 e 2 1.0000 +alter table t1 rename index e to b; +alter table t1 change b c varchar(200), change c d varchar(200), change d e varchar(200) ; +show create table t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) NOT NULL, + `c` varchar(200) DEFAULT NULL, + `d` varchar(200) DEFAULT NULL, + `e` varchar(200) DEFAULT NULL, + PRIMARY KEY (`a`), + KEY `d` (`c`), + KEY `b` (`d`), + KEY `c` (`e`,`c`) +) ENGINE=InnoDB DEFAULT CHARSET=latin1 COLLATE=latin1_swedish_ci +select * from mysql.index_stats order by index_name, prefix_arity; +db_name table_name index_name prefix_arity avg_frequency +test t1 PRIMARY 1 1.0000 +test t1 b 1 20.0000 +test t1 b 2 1.0000 +test t1 c 1 10.0000 +test t1 c 2 1.0000 +test t1 c 3 1.0000 +test t1 d 1 1.0000 +test t1 d 2 1.0000 +# Test having a conflicting temporary name +insert into mysql.index_stats (db_name,table_name,index_name,prefix_arity) values ("test","t1",concat("#sql_tmp_name#1",char(0)),1); +alter table t1 rename index c to d, rename index d to c; +select * from mysql.index_stats order by index_name, prefix_arity; +db_name table_name index_name prefix_arity avg_frequency +test t1 PRIMARY 1 1.0000 +test t1 b 1 20.0000 +test t1 b 2 1.0000 +test t1 c 1 1.0000 +test t1 c 2 1.0000 +test t1 d 1 10.0000 +test t1 d 2 1.0000 +test t1 d 3 1.0000 +drop table t1; +select * from mysql.index_stats order by index_name, prefix_arity; +db_name table_name index_name prefix_arity avg_frequency +# +# Test of adding key that replaces foreign key +# +CREATE TABLE t1 (aaaa INT, b INT, KEY(b), FOREIGN KEY(aaaa) REFERENCES t1(b)) ENGINE=InnoDB; +ANALYZE TABLE t1 PERSISTENT FOR ALL; +Table Op Msg_type Msg_text +test.t1 analyze status Engine-independent statistics collected +test.t1 analyze status OK +SELECT index_name FROM mysql.index_stats WHERE table_name = 't1' order by index_name; +index_name +aaaa +b +ALTER TABLE t1 ADD KEY idx(aaaa); +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `aaaa` int(11) DEFAULT NULL, + `b` int(11) DEFAULT NULL, + KEY `b` (`b`), + KEY `idx` (`aaaa`), + CONSTRAINT `t1_ibfk_1` FOREIGN KEY (`aaaa`) REFERENCES `t1` (`b`) +) ENGINE=InnoDB DEFAULT CHARSET=latin1 COLLATE=latin1_swedish_ci +SELECT index_name FROM mysql.index_stats WHERE table_name = 't1' order by index_name; +index_name +b +truncate table mysql.index_stats; +ANALYZE TABLE t1 PERSISTENT FOR ALL; +Table Op Msg_type Msg_text +test.t1 analyze status Engine-independent statistics collected +test.t1 analyze status OK +SELECT index_name FROM mysql.index_stats WHERE table_name = 't1' order by index_name; +index_name +b +idx +ALTER TABLE t1 DROP KEY idx; +ERROR HY000: Cannot drop index 'idx': needed in a foreign key constraint +DROP TABLE t1; +# +# Check index rename where name is not changed +# +create or replace table t1 (a int primary key, b int, c int, key b (b,c)); +show create table t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) NOT NULL, + `b` int(11) DEFAULT NULL, + `c` int(11) DEFAULT NULL, + PRIMARY KEY (`a`), + KEY `b` (`b`,`c`) +) ENGINE=MyISAM DEFAULT CHARSET=latin1 COLLATE=latin1_swedish_ci +analyze table t1 persistent for all; +Table Op Msg_type Msg_text +test.t1 analyze status Engine-independent statistics collected +test.t1 analyze status Table is already up to date +select * from mysql.index_stats where table_name= "t1"; +db_name table_name index_name prefix_arity avg_frequency +test t1 PRIMARY 1 1.0000 +test t1 b 1 NULL +test t1 b 2 NULL +alter ignore table t1 rename key `b` to b, LOCK=shared; +select * from mysql.index_stats where table_name= "t1"; +db_name table_name index_name prefix_arity avg_frequency +test t1 PRIMARY 1 1.0000 +test t1 b 1 NULL +test t1 b 2 NULL +alter ignore table t1 rename key `b` to `B`, LOCK=shared; +select * from mysql.index_stats where table_name= "t1"; +db_name table_name index_name prefix_arity avg_frequency +test t1 PRIMARY 1 1.0000 +test t1 B 1 NULL +test t1 B 2 NULL +drop table t1; +# +# End of 10.6 tests +# diff --git a/mysql-test/main/analyze.test b/mysql-test/main/analyze.test index 85a88158162..e3b776f11ca 100644 --- a/mysql-test/main/analyze.test +++ b/mysql-test/main/analyze.test @@ -1,3 +1,6 @@ +--source include/have_sequence.inc +--source include/have_innodb.inc + # # Bug #10901 Analyze Table on new table destroys table # This is minimal test case to get error @@ -87,3 +90,185 @@ optimize table t1 extended; drop table t1; --echo End of 5.0 tests + +--echo # +--echo # Test analyze of text column (not yet supported) +--echo # + +set optimizer_use_condition_selectivity=4; +set histogram_type='single_prec_hb'; +set histogram_size=255; + +create table t1 (a int not null, t tinytext, tx text); +insert into t1 select seq+1, repeat('X',seq*5), repeat('X',seq*10) from seq_0_to_50; +insert into t1 select seq+100, repeat('X',5), "" from seq_1_to_10; +analyze table t1; +explain select count(*) from t1 where t='XXXXXX'; +select column_name, min_value, max_value, hist_size from mysql.column_stats where table_name='t1'; + +drop table t1; + +set use_stat_tables=default; +set histogram_type=default; +set histogram_size=default; + +--echo # +--echo # MDEV-31957 Concurrent ALTER and ANALYZE collecting statistics can +--echo # result in stale statistical data +--echo # + +CREATE TABLE t1 (a INT, b VARCHAR(128)); +INSERT INTO t1 SELECT seq, CONCAT('s',seq) FROM seq_1_to_100; + +# We have to disable query log as the ANALYZE TABLE can be run in different +# order. The important thing is what is finally in column_stats +--disable_result_log +--connect (con1,localhost,root,,) +--send ALTER TABLE t1 MODIFY b BLOB + +--connection default +ANALYZE TABLE t1 PERSISTENT FOR ALL; + +--connection con1 +--reap +ANALYZE TABLE t1 PERSISTENT FOR ALL; +--connection default +--disconnect con1 +--enable_result_log +select db_name,table_name,column_name from mysql.column_stats; +drop table t1; + +--echo # +--echo # Testing swapping columns +--echo # + +create or replace table t1 (a int primary key, b varchar(100), c varchar(100), d varchar(100)) engine=innodb; +insert into t1 select seq, repeat('b',seq),repeat('c',mod(seq,5)), repeat('d',mod(seq,10)) from seq_1_to_100; +ANALYZE TABLE t1 PERSISTENT FOR ALL; +select db_name,table_name,column_name,avg_length from mysql.column_stats order by column_name; +alter table t1 change b c varchar(200), change c b varchar(200); +select db_name,table_name,column_name,avg_length from mysql.column_stats order by column_name; +alter table t1 change b c varchar(200), change c d varchar(200), change d b varchar(200) ; +select db_name,table_name,column_name,avg_length from mysql.column_stats order by column_name; +alter table t1 change b c varchar(200), change c d varchar(200), change d e varchar(200) ; +select db_name,table_name,column_name,avg_length from mysql.column_stats order by column_name; +alter table t1 change e d varchar(200), drop column d; +select db_name,table_name,column_name,avg_length from mysql.column_stats order by column_name; + +--echo # Test having non existing column in column_stats + +insert into mysql.column_stats (db_name,table_name,column_name) values ("test","t1","b"); +alter table t1 change c d varchar(200), change d b varchar(200); +select db_name,table_name,column_name,avg_length from mysql.column_stats order by column_name; + +--echo # Test having a conflicting temporary name +insert into mysql.column_stats (db_name,table_name,column_name) values ("test","t1",concat("#sql_tmp_name#1",char(0))); +alter table t1 change d b varchar(200), change b d varchar(200); +select db_name,table_name,column_name,avg_length from mysql.column_stats order by column_name; + +drop table t1; +truncate table mysql.column_stats; + +create or replace table t1 (a int primary key, b varchar(100), c varchar(100), d varchar(100)) engine=myisam; +insert into t1 select seq, repeat('b',seq),repeat('c',mod(seq,5)), repeat('d',mod(seq,10)) from seq_1_to_100; +ANALYZE TABLE t1 PERSISTENT FOR ALL; +select db_name,table_name,column_name,avg_length from mysql.column_stats order by column_name; +alter table t1 change b c varchar(200), change c b varchar(200); +select db_name,table_name,column_name,avg_length from mysql.column_stats order by column_name; +analyze table t1 persistent for columns(b,c) indexes all; +alter table t1 change b c varchar(200), change c d varchar(200), change d b varchar(200) ; +select db_name,table_name,column_name,avg_length from mysql.column_stats order by column_name; +analyze table t1 persistent for columns(d) indexes all; +alter table t1 change b c varchar(200), change c d varchar(200), change d e varchar(200) ; +select db_name,table_name,column_name,avg_length from mysql.column_stats order by column_name; +alter table t1 change e d varchar(200), drop column d; +select db_name,table_name,column_name,avg_length from mysql.column_stats order by column_name; +drop table t1; +truncate table mysql.column_stats; + +create table t1 (a int, b blob, unique(b)) engine= innodb; +analyze table t1 persistent for all; +select column_name from mysql.column_stats where table_name = 't1'; +drop table t1; + +create table t1 (a int, b blob, c int generated always as (length(b)) virtual) engine= innodb; +analyze table t1 persistent for all; +select column_name from mysql.column_stats where table_name = 't1'; +drop table t1; + +CREATE or replace TABLE t1 (a INT, b CHAR(8)); +ANALYZE TABLE t1 PERSISTENT FOR ALL; +ALTER TABLE t1 CHANGE b c INT, ORDER BY b; +SELECT db_name, table_name, column_name FROM mysql.column_stats where table_name = 't1'; +drop table t1; + +CREATE or replace TABLE t1 (a INT, b CHAR(8)); +ANALYZE TABLE t1 PERSISTENT FOR ALL; +ALTER TABLE t1 RENAME COLUMN b to c, ALGORITHM=COPY; +SELECT db_name, table_name, column_name FROM mysql.column_stats where table_name = 't1'; +drop table t1; + +--echo # +--echo # Testing swapping indexes +--echo # + +create or replace table t1 (a int primary key, b varchar(100), c varchar(100), d varchar(100), index (b), index(c), index(d,b)) engine=innodb; +insert into t1 select seq, repeat('b',seq),repeat('c',mod(seq,5)), repeat('d',mod(seq,10)) from seq_1_to_100; +ANALYZE TABLE t1 PERSISTENT FOR ALL; +select * from mysql.index_stats order by index_name, prefix_arity; +alter table t1 rename index b to c, rename index c to d, rename index d to b; +select * from mysql.index_stats order by index_name; + +alter table t1 rename index b to c, rename index c to d, rename index d to e; +select * from mysql.index_stats order by index_name, prefix_arity; +alter table t1 rename index e to b; +alter table t1 change b c varchar(200), change c d varchar(200), change d e varchar(200) ; +show create table t1; +select * from mysql.index_stats order by index_name, prefix_arity; + +--echo # Test having a conflicting temporary name +insert into mysql.index_stats (db_name,table_name,index_name,prefix_arity) values ("test","t1",concat("#sql_tmp_name#1",char(0)),1); +alter table t1 rename index c to d, rename index d to c; +select * from mysql.index_stats order by index_name, prefix_arity; +drop table t1; +select * from mysql.index_stats order by index_name, prefix_arity; + +--echo # +--echo # Test of adding key that replaces foreign key +--echo # + +CREATE TABLE t1 (aaaa INT, b INT, KEY(b), FOREIGN KEY(aaaa) REFERENCES t1(b)) ENGINE=InnoDB; +ANALYZE TABLE t1 PERSISTENT FOR ALL; + +SELECT index_name FROM mysql.index_stats WHERE table_name = 't1' order by index_name; + +ALTER TABLE t1 ADD KEY idx(aaaa); +SHOW CREATE TABLE t1; + +SELECT index_name FROM mysql.index_stats WHERE table_name = 't1' order by index_name; + +truncate table mysql.index_stats; +ANALYZE TABLE t1 PERSISTENT FOR ALL; +SELECT index_name FROM mysql.index_stats WHERE table_name = 't1' order by index_name; + +--error ER_DROP_INDEX_FK +ALTER TABLE t1 DROP KEY idx; +DROP TABLE t1; + +--echo # +--echo # Check index rename where name is not changed +--echo # + +create or replace table t1 (a int primary key, b int, c int, key b (b,c)); +show create table t1; +analyze table t1 persistent for all; +select * from mysql.index_stats where table_name= "t1"; +alter ignore table t1 rename key `b` to b, LOCK=shared; +select * from mysql.index_stats where table_name= "t1"; +alter ignore table t1 rename key `b` to `B`, LOCK=shared; +select * from mysql.index_stats where table_name= "t1"; +drop table t1; + +--echo # +--echo # End of 10.6 tests +--echo # diff --git a/mysql-test/main/brackets.result b/mysql-test/main/brackets.result index 0403ce81d1d..1f1922416a1 100644 --- a/mysql-test/main/brackets.result +++ b/mysql-test/main/brackets.result @@ -512,7 +512,7 @@ drop table t1; # MDEV-18689: parenthesis around table names and derived tables # select * from ( mysql.db ); -Host Db User Select_priv Insert_priv Update_priv Delete_priv Create_priv Drop_priv Grant_priv References_priv Index_priv Alter_priv Create_tmp_table_priv Lock_tables_priv Create_view_priv Show_view_priv Create_routine_priv Alter_routine_priv Execute_priv Event_priv Trigger_priv Delete_history_priv +Host Db User Select_priv Insert_priv Update_priv Delete_priv Create_priv Drop_priv Grant_priv References_priv Index_priv Alter_priv Create_tmp_table_priv Lock_tables_priv Create_view_priv Show_view_priv Create_routine_priv Alter_routine_priv Execute_priv Event_priv Trigger_priv Delete_history_priv Show_create_routine_priv create table t1 (a int); insert into t1 values (7), (2), (7); select * from (t1); diff --git a/mysql-test/main/column_compression.inc b/mysql-test/main/column_compression.inc index 13952b739ae..27e5fc70837 100644 --- a/mysql-test/main/column_compression.inc +++ b/mysql-test/main/column_compression.inc @@ -70,7 +70,8 @@ TRUNCATE TABLE t1; SET column_compression_zlib_level= 1; INSERT INTO t1 VALUES(REPEAT('ab', 1000)); SELECT * FROM INFORMATION_SCHEMA.SESSION_STATUS WHERE VARIABLE_NAME IN('Column_compressions', 'Column_decompressions'); -SELECT DATA_LENGTH FROM INFORMATION_SCHEMA.TABLES WHERE TABLE_SCHEMA='test' AND TABLE_NAME='t1'; +# This is is using < as DATA_LENGTH produces different results on s390x-ubuntu-2004 +SELECT DATA_LENGTH < 100 FROM INFORMATION_SCHEMA.TABLES WHERE TABLE_SCHEMA='test' AND TABLE_NAME='t1'; TRUNCATE TABLE t1; SET column_compression_zlib_level= 9; diff --git a/mysql-test/main/column_compression.result b/mysql-test/main/column_compression.result index e6bc6b6cb58..7d846caedde 100644 --- a/mysql-test/main/column_compression.result +++ b/mysql-test/main/column_compression.result @@ -133,9 +133,9 @@ SELECT * FROM INFORMATION_SCHEMA.SESSION_STATUS WHERE VARIABLE_NAME IN('Column_c VARIABLE_NAME VARIABLE_VALUE COLUMN_COMPRESSIONS 3 COLUMN_DECOMPRESSIONS 12 -SELECT DATA_LENGTH FROM INFORMATION_SCHEMA.TABLES WHERE TABLE_SCHEMA='test' AND TABLE_NAME='t1'; -DATA_LENGTH -40 +SELECT DATA_LENGTH < 100 FROM INFORMATION_SCHEMA.TABLES WHERE TABLE_SCHEMA='test' AND TABLE_NAME='t1'; +DATA_LENGTH < 100 +1 TRUNCATE TABLE t1; SET column_compression_zlib_level= 9; INSERT INTO t1 VALUES(REPEAT('ab', 1000)); @@ -348,9 +348,9 @@ SELECT * FROM INFORMATION_SCHEMA.SESSION_STATUS WHERE VARIABLE_NAME IN('Column_c VARIABLE_NAME VARIABLE_VALUE COLUMN_COMPRESSIONS 3 COLUMN_DECOMPRESSIONS 12 -SELECT DATA_LENGTH FROM INFORMATION_SCHEMA.TABLES WHERE TABLE_SCHEMA='test' AND TABLE_NAME='t1'; -DATA_LENGTH -40 +SELECT DATA_LENGTH < 100 FROM INFORMATION_SCHEMA.TABLES WHERE TABLE_SCHEMA='test' AND TABLE_NAME='t1'; +DATA_LENGTH < 100 +1 TRUNCATE TABLE t1; SET column_compression_zlib_level= 9; INSERT INTO t1 VALUES(REPEAT('ab', 1000)); @@ -563,9 +563,9 @@ SELECT * FROM INFORMATION_SCHEMA.SESSION_STATUS WHERE VARIABLE_NAME IN('Column_c VARIABLE_NAME VARIABLE_VALUE COLUMN_COMPRESSIONS 3 COLUMN_DECOMPRESSIONS 12 -SELECT DATA_LENGTH FROM INFORMATION_SCHEMA.TABLES WHERE TABLE_SCHEMA='test' AND TABLE_NAME='t1'; -DATA_LENGTH -40 +SELECT DATA_LENGTH < 100 FROM INFORMATION_SCHEMA.TABLES WHERE TABLE_SCHEMA='test' AND TABLE_NAME='t1'; +DATA_LENGTH < 100 +1 TRUNCATE TABLE t1; SET column_compression_zlib_level= 9; INSERT INTO t1 VALUES(REPEAT('ab', 1000)); @@ -778,9 +778,9 @@ SELECT * FROM INFORMATION_SCHEMA.SESSION_STATUS WHERE VARIABLE_NAME IN('Column_c VARIABLE_NAME VARIABLE_VALUE COLUMN_COMPRESSIONS 3 COLUMN_DECOMPRESSIONS 12 -SELECT DATA_LENGTH FROM INFORMATION_SCHEMA.TABLES WHERE TABLE_SCHEMA='test' AND TABLE_NAME='t1'; -DATA_LENGTH -40 +SELECT DATA_LENGTH < 100 FROM INFORMATION_SCHEMA.TABLES WHERE TABLE_SCHEMA='test' AND TABLE_NAME='t1'; +DATA_LENGTH < 100 +1 TRUNCATE TABLE t1; SET column_compression_zlib_level= 9; INSERT INTO t1 VALUES(REPEAT('ab', 1000)); @@ -993,9 +993,9 @@ SELECT * FROM INFORMATION_SCHEMA.SESSION_STATUS WHERE VARIABLE_NAME IN('Column_c VARIABLE_NAME VARIABLE_VALUE COLUMN_COMPRESSIONS 3 COLUMN_DECOMPRESSIONS 12 -SELECT DATA_LENGTH FROM INFORMATION_SCHEMA.TABLES WHERE TABLE_SCHEMA='test' AND TABLE_NAME='t1'; -DATA_LENGTH -60 +SELECT DATA_LENGTH < 100 FROM INFORMATION_SCHEMA.TABLES WHERE TABLE_SCHEMA='test' AND TABLE_NAME='t1'; +DATA_LENGTH < 100 +1 TRUNCATE TABLE t1; SET column_compression_zlib_level= 9; INSERT INTO t1 VALUES(REPEAT('ab', 1000)); @@ -1209,9 +1209,9 @@ SELECT * FROM INFORMATION_SCHEMA.SESSION_STATUS WHERE VARIABLE_NAME IN('Column_c VARIABLE_NAME VARIABLE_VALUE COLUMN_COMPRESSIONS 3 COLUMN_DECOMPRESSIONS 12 -SELECT DATA_LENGTH FROM INFORMATION_SCHEMA.TABLES WHERE TABLE_SCHEMA='test' AND TABLE_NAME='t1'; -DATA_LENGTH -36 +SELECT DATA_LENGTH < 100 FROM INFORMATION_SCHEMA.TABLES WHERE TABLE_SCHEMA='test' AND TABLE_NAME='t1'; +DATA_LENGTH < 100 +1 TRUNCATE TABLE t1; SET column_compression_zlib_level= 9; INSERT INTO t1 VALUES(REPEAT('ab', 1000)); diff --git a/mysql-test/main/column_compression.test b/mysql-test/main/column_compression.test index f43cfd011d7..642399be1f6 100644 --- a/mysql-test/main/column_compression.test +++ b/mysql-test/main/column_compression.test @@ -1,5 +1,6 @@ --source include/have_innodb.inc --source include/have_csv.inc +--source include/have_normal_bzip.inc let $MYSQLD_DATADIR= `select @@datadir`; diff --git a/mysql-test/main/column_compression_rpl.test b/mysql-test/main/column_compression_rpl.test index 86c73a77dbd..df8e889016b 100644 --- a/mysql-test/main/column_compression_rpl.test +++ b/mysql-test/main/column_compression_rpl.test @@ -1,5 +1,6 @@ --source include/have_innodb.inc --source include/master-slave.inc +--source include/have_normal_bzip.inc --let $engine_type= myisam --let $engine_type2= innodb diff --git a/mysql-test/main/compare.result b/mysql-test/main/compare.result index b8883784d21..70664e2cc18 100644 --- a/mysql-test/main/compare.result +++ b/mysql-test/main/compare.result @@ -4,6 +4,8 @@ insert into t1 values ('000000000001'),('000000000002'); explain select * from t1 where id=000000000001; id select_type table type possible_keys key key_len ref rows Extra 1 SIMPLE t1 index PRIMARY PRIMARY 12 NULL 2 Using where; Using index +Warnings: +Note 1105 Cannot use key `PRIMARY` part[0] for lookup: `test`.`t1`.`id` of type `char` = "1" of type `bigint` select * from t1 where id=000000000001; id 000000000001 diff --git a/mysql-test/main/connect.result b/mysql-test/main/connect.result index 74387168d98..1c5045ebe0e 100644 --- a/mysql-test/main/connect.result +++ b/mysql-test/main/connect.result @@ -104,12 +104,12 @@ update mysql.user set plugin="", authentication_string="", password=old_password flush privileges; show grants for test@localhost; Grants for test@localhost -GRANT ALL PRIVILEGES ON *.* TO `test`@`localhost` IDENTIFIED BY PASSWORD '2f27438961437573' +GRANT SELECT, INSERT, UPDATE, DELETE, CREATE, DROP, RELOAD, SHUTDOWN, PROCESS, FILE, REFERENCES, INDEX, ALTER, SHOW DATABASES, SUPER, CREATE TEMPORARY TABLES, LOCK TABLES, EXECUTE, REPLICATION SLAVE, BINLOG MONITOR, CREATE VIEW, SHOW VIEW, CREATE ROUTINE, ALTER ROUTINE, CREATE USER, EVENT, TRIGGER, CREATE TABLESPACE, DELETE HISTORY, SET USER, FEDERATED ADMIN, CONNECTION ADMIN, READ_ONLY ADMIN, REPLICATION SLAVE ADMIN, REPLICATION MASTER ADMIN, BINLOG ADMIN, BINLOG REPLAY, SLAVE MONITOR ON *.* TO `test`@`localhost` IDENTIFIED BY PASSWORD '2f27438961437573' update mysql.user set plugin='mysql_old_password' where user='test'; flush privileges; show grants for test@localhost; Grants for test@localhost -GRANT ALL PRIVILEGES ON *.* TO `test`@`localhost` IDENTIFIED BY PASSWORD '2f27438961437573' +GRANT SELECT, INSERT, UPDATE, DELETE, CREATE, DROP, RELOAD, SHUTDOWN, PROCESS, FILE, REFERENCES, INDEX, ALTER, SHOW DATABASES, SUPER, CREATE TEMPORARY TABLES, LOCK TABLES, EXECUTE, REPLICATION SLAVE, BINLOG MONITOR, CREATE VIEW, SHOW VIEW, CREATE ROUTINE, ALTER ROUTINE, CREATE USER, EVENT, TRIGGER, CREATE TABLESPACE, DELETE HISTORY, SET USER, FEDERATED ADMIN, CONNECTION ADMIN, READ_ONLY ADMIN, REPLICATION SLAVE ADMIN, REPLICATION MASTER ADMIN, BINLOG ADMIN, BINLOG REPLAY, SLAVE MONITOR ON *.* TO `test`@`localhost` IDENTIFIED BY PASSWORD '2f27438961437573' connect con10,localhost,test,gambling2,; connect con5,localhost,test,gambling2,mysql; set password=""; diff --git a/mysql-test/main/create.result b/mysql-test/main/create.result index d6c68fdd917..b57c898c384 100644 --- a/mysql-test/main/create.result +++ b/mysql-test/main/create.result @@ -1083,12 +1083,13 @@ t1 CREATE TABLE `t1` ( `STAGE` tinyint(2) NOT NULL, `MAX_STAGE` tinyint(2) NOT NULL, `PROGRESS` decimal(7,3) NOT NULL, - `MEMORY_USED` bigint(7) NOT NULL, - `MAX_MEMORY_USED` bigint(7) NOT NULL, - `EXAMINED_ROWS` int(7) NOT NULL, - `QUERY_ID` bigint(4) NOT NULL, + `MEMORY_USED` bigint(10) NOT NULL, + `MAX_MEMORY_USED` bigint(10) NOT NULL, + `EXAMINED_ROWS` bigint(10) NOT NULL, + `SENT_ROWS` bigint(10) NOT NULL, + `QUERY_ID` bigint(10) NOT NULL, `INFO_BINARY` blob, - `TID` bigint(4) NOT NULL + `TID` bigint(10) NOT NULL ) DEFAULT CHARSET=utf8mb3 COLLATE=utf8mb3_general_ci drop table t1; create temporary table t1 like information_schema.processlist; @@ -1107,12 +1108,13 @@ t1 CREATE TEMPORARY TABLE `t1` ( `STAGE` tinyint(2) NOT NULL, `MAX_STAGE` tinyint(2) NOT NULL, `PROGRESS` decimal(7,3) NOT NULL, - `MEMORY_USED` bigint(7) NOT NULL, - `MAX_MEMORY_USED` bigint(7) NOT NULL, - `EXAMINED_ROWS` int(7) NOT NULL, - `QUERY_ID` bigint(4) NOT NULL, + `MEMORY_USED` bigint(10) NOT NULL, + `MAX_MEMORY_USED` bigint(10) NOT NULL, + `EXAMINED_ROWS` bigint(10) NOT NULL, + `SENT_ROWS` bigint(10) NOT NULL, + `QUERY_ID` bigint(10) NOT NULL, `INFO_BINARY` blob, - `TID` bigint(4) NOT NULL + `TID` bigint(10) NOT NULL ) DEFAULT CHARSET=utf8mb3 COLLATE=utf8mb3_general_ci drop table t1; create table t1 like information_schema.character_sets; diff --git a/mysql-test/main/ctype_collate.result b/mysql-test/main/ctype_collate.result index 29d27fd608b..af2735bc03b 100644 --- a/mysql-test/main/ctype_collate.result +++ b/mysql-test/main/ctype_collate.result @@ -606,6 +606,8 @@ id select_type table type possible_keys key key_len ref rows Extra EXPLAIN SELECT * FROM t1 WHERE s2='a' COLLATE latin1_german1_ci; id select_type table type possible_keys key key_len ref rows Extra 1 SIMPLE t1 ALL s2 NULL NULL NULL 10 Using where +Warnings: +Note 1105 Cannot use key `s2` part[0] for lookup: `test`.`t1`.`s2` of collation `latin1_swedish_ci` = "'a' collate latin1_german1_ci" of collation `latin1_german1_ci` EXPLAIN SELECT * FROM t1 WHERE s1 BETWEEN 'a' AND 'b' COLLATE latin1_german1_ci; id select_type table type possible_keys key key_len ref rows Extra 1 SIMPLE t1 range s1 s1 11 NULL 2 Using index condition diff --git a/mysql-test/main/date_formats.result b/mysql-test/main/date_formats.result index a9e400805ca..9db6b3212e3 100644 --- a/mysql-test/main/date_formats.result +++ b/mysql-test/main/date_formats.result @@ -555,3 +555,76 @@ time_format('01 02:02:02', '%T') select time_format('2001-01-01 02:02:02', '%T'); time_format('2001-01-01 02:02:02', '%T') 02:02:02 +# +# End of 10.2 test +# +# +# MDEV-31684 Add timezone information to DATE_FORMAT +# +SET @old_timezone= @@time_zone; +# Using named timezones +SET TIME_ZONE='Japan'; +SELECT DATE_FORMAT('2009-10-04 22:23:00', '%z %Z') AS current_timezone; +current_timezone ++0900 JST +SET @@time_zone='Europe/Moscow'; +SELECT DATE_FORMAT('1965-02-17 22:23:00', '%z %Z') AS current_timezone; +current_timezone ++0300 MSK +SELECT DATE_FORMAT('1965-12-31 22:23:00', '%z %Z') AS current_timezone; +current_timezone ++0300 MSK +SELECT DATE_FORMAT('1985-06-01', '%z %Z'); +DATE_FORMAT('1985-06-01', '%z %Z') ++0400 MSD +# Using positive and negative offset +SET TIME_ZONE= '-05:30'; +SELECT DATE_FORMAT('2009-10-04 22:23:00', '%z %Z') AS current_timezone; +current_timezone +-0530 -05:30 +SET TIME_ZONE= '+04:30'; +SELECT DATE_FORMAT('2009-10-04 22:23:00', '%z %Z') AS current_timezone; +current_timezone ++0430 +04:30 +# Using UTC +SET TIME_ZONE='UTC'; +SELECT DATE_FORMAT('2009-10-04 22:23:00', '%z %Z') AS current_timezone; +current_timezone ++0000 UTC +SET @@time_zone= @old_timezone; +# More timezone test: +# +# Check for time zone with leap seconds +# +set time_zone='Europe/Moscow'; +SELECT DATE_FORMAT('2023-03-01 01:30:00', '%z %Z'); +DATE_FORMAT('2023-03-01 01:30:00', '%z %Z') ++0300 MSK +SELECT DATE_FORMAT('2023-04-01 01:30:00', '%z %Z'); +DATE_FORMAT('2023-04-01 01:30:00', '%z %Z') ++0400 MSD +set time_zone='leap/Europe/Moscow'; +SELECT DATE_FORMAT('2023-03-01 01:30:00', '%z %Z'); +DATE_FORMAT('2023-03-01 01:30:00', '%z %Z') ++0300 MSK +SELECT DATE_FORMAT('2023-04-01 01:30:00', '%z %Z'); +DATE_FORMAT('2023-04-01 01:30:00', '%z %Z') ++0400 MSD +# +# Values around and in spring time-gap +# +set time_zone='MET'; +# Normal value with DST +SELECT DATE_FORMAT('2003-03-30 01:59:59', '%z %Z'); +DATE_FORMAT('2003-03-30 01:59:59', '%z %Z') ++0100 MET +# Values around and in spring time-gap +SELECT DATE_FORMAT('2023-03-26 01:59:59', '%z %Z'); +DATE_FORMAT('2023-03-26 01:59:59', '%z %Z') ++0100 MET +SELECT DATE_FORMAT('2023-03-26 03:00:00', '%z %Z'); +DATE_FORMAT('2023-03-26 03:00:00', '%z %Z') ++0200 MEST +# +# End of 11.3 test +# diff --git a/mysql-test/main/date_formats.test b/mysql-test/main/date_formats.test index 0e6f0f8ec85..691966de892 100644 --- a/mysql-test/main/date_formats.test +++ b/mysql-test/main/date_formats.test @@ -256,3 +256,72 @@ select time_format('2001-01-01 02:02:02', '%d %T'); select time_format('01 02:02:02', '%d %T'); select time_format('01 02:02:02', '%T'); select time_format('2001-01-01 02:02:02', '%T'); + +--echo # +--echo # End of 10.2 test +--echo # + +--echo # +--echo # MDEV-31684 Add timezone information to DATE_FORMAT +--echo # + +SET @old_timezone= @@time_zone; + + +--echo # Using named timezones + +SET TIME_ZONE='Japan'; +SELECT DATE_FORMAT('2009-10-04 22:23:00', '%z %Z') AS current_timezone; + +SET @@time_zone='Europe/Moscow'; +SELECT DATE_FORMAT('1965-02-17 22:23:00', '%z %Z') AS current_timezone; +SELECT DATE_FORMAT('1965-12-31 22:23:00', '%z %Z') AS current_timezone; +SELECT DATE_FORMAT('1985-06-01', '%z %Z'); + +--echo # Using positive and negative offset + +SET TIME_ZONE= '-05:30'; +SELECT DATE_FORMAT('2009-10-04 22:23:00', '%z %Z') AS current_timezone; + +SET TIME_ZONE= '+04:30'; +SELECT DATE_FORMAT('2009-10-04 22:23:00', '%z %Z') AS current_timezone; + + +--echo # Using UTC + +SET TIME_ZONE='UTC'; +SELECT DATE_FORMAT('2009-10-04 22:23:00', '%z %Z') AS current_timezone; + +SET @@time_zone= @old_timezone; + +--echo # More timezone test: + +--echo # +--echo # Check for time zone with leap seconds +--echo # +set time_zone='Europe/Moscow'; + +SELECT DATE_FORMAT('2023-03-01 01:30:00', '%z %Z'); +SELECT DATE_FORMAT('2023-04-01 01:30:00', '%z %Z'); + +set time_zone='leap/Europe/Moscow'; +SELECT DATE_FORMAT('2023-03-01 01:30:00', '%z %Z'); +SELECT DATE_FORMAT('2023-04-01 01:30:00', '%z %Z'); + +--echo # +--echo # Values around and in spring time-gap +--echo # + +set time_zone='MET'; + +--echo # Normal value with DST +SELECT DATE_FORMAT('2003-03-30 01:59:59', '%z %Z'); + +--echo # Values around and in spring time-gap +SELECT DATE_FORMAT('2023-03-26 01:59:59', '%z %Z'); +SELECT DATE_FORMAT('2023-03-26 03:00:00', '%z %Z'); + + +--echo # +--echo # End of 11.3 test +--echo # diff --git a/mysql-test/main/delayed.result b/mysql-test/main/delayed.result index d5397e73a22..472a3cd53d5 100644 --- a/mysql-test/main/delayed.result +++ b/mysql-test/main/delayed.result @@ -355,97 +355,6 @@ ERROR 42S01: Table 't1' already exists DROP TABLE t2; DROP TABLE t1; # -# Bug#54332 Deadlock with two connections doing LOCK TABLE+INSERT DELAYED -# -# This test is not supposed to work under --ps-protocol since -# INSERT DELAYED doesn't work under LOCK TABLES with this protocol. -DROP TABLE IF EXISTS t1, t2; -CREATE TABLE t1 (a INT); -CREATE TABLE t2 (a INT); -CREATE TABLE t3 (a INT); -# Test 1: Using LOCK TABLE -connect con1, localhost, root; -LOCK TABLE t1 WRITE; -connection default; -LOCK TABLE t2 WRITE; -# Sending: -INSERT DELAYED INTO t1 VALUES (1); -connection con1; -# Wait until INSERT DELAYED is blocked on table 't1'. -INSERT DELAYED INTO t2 VALUES (1); -ERROR 40001: Deadlock found when trying to get lock; try restarting transaction -UNLOCK TABLES; -connection default; -# Reaping: INSERT DELAYED INTO t1 VALUES (1) -UNLOCK TABLES; -# Test 2: Using ALTER TABLE -START TRANSACTION; -SELECT * FROM t1 WHERE a=0; -a -connection con1; -# Sending: -ALTER TABLE t1 MODIFY a INT UNSIGNED, LOCK=SHARED;; -connection default; -# Wait until ALTER TABLE is blocked on table 't1'. -INSERT DELAYED INTO t1 VALUES (3); -ERROR 40001: Deadlock found when trying to get lock; try restarting transaction -COMMIT; -connection con1; -# Reaping: ALTER TABLE t1 COMMENT 'test' -# Test 3: Using RENAME TABLE -connection default; -START TRANSACTION; -INSERT INTO t2 VALUES (1); -connection con1; -# Sending: -RENAME TABLE t1 to t5, t2 to t4; -connection default; -# Wait until RENAME TABLE is blocked on table 't1'. -INSERT DELAYED INTO t1 VALUES (4); -ERROR 40001: Deadlock found when trying to get lock; try restarting transaction -COMMIT; -connection con1; -# Reaping: RENAME TABLE t1 to t5, t2 to t4 -connection default; -# Reverting the renames -RENAME TABLE t5 to t1, t4 to t2; -# Test 4: Two INSERT DELAYED on the same table -START TRANSACTION; -INSERT INTO t2 VALUES (1); -connect con2, localhost, root; -LOCK TABLE t1 WRITE, t2 WRITE; -connection con1; -# Wait until LOCK TABLE is blocked on table 't2'. -INSERT DELAYED INTO t1 VALUES (5); -connection default; -# Wait until INSERT DELAYED is blocked on table 't1'. -INSERT DELAYED INTO t1 VALUES (6); -ERROR 40001: Deadlock found when trying to get lock; try restarting transaction -COMMIT; -connection con2; -# Reaping: LOCK TABLE t1 WRITE, t2 WRITE -UNLOCK TABLES; -connection con1; -# Reaping: INSERT DELAYED INTO t1 VALUES (5) -connection default; -# Test 5: LOCK TABLES + INSERT DELAYED in one connection. -# This test has triggered some asserts in metadata locking -# subsystem at some point in time.. -LOCK TABLE t1 WRITE; -INSERT DELAYED INTO t2 VALUES (7); -UNLOCK TABLES; -SET AUTOCOMMIT= 0; -LOCK TABLE t1 WRITE; -INSERT DELAYED INTO t2 VALUES (8); -UNLOCK TABLES; -SET AUTOCOMMIT= 1; -connection con2; -disconnect con2; -connection con1; -disconnect con1; -connection default; -DROP TABLE t1, t2, t3; -# # Test for bug #56251 "Deadlock with INSERT DELAYED and MERGE tables". # connect con1,localhost,root,,; diff --git a/mysql-test/main/delayed.test b/mysql-test/main/delayed.test index 0ffe6d7347d..50d1c1e8c0a 100644 --- a/mysql-test/main/delayed.test +++ b/mysql-test/main/delayed.test @@ -408,6 +408,9 @@ DROP TABLE t2; DROP TABLE t1; +# The following test is disabled as it fails randomly +if (0) +{ --echo # --echo # Bug#54332 Deadlock with two connections doing LOCK TABLE+INSERT DELAYED --echo # @@ -566,6 +569,7 @@ connection default; DROP TABLE t1, t2, t3; --enable_ps_protocol --enable_view_protocol +} --echo # --echo # Test for bug #56251 "Deadlock with INSERT DELAYED and MERGE tables". diff --git a/mysql-test/main/delete_returning.result b/mysql-test/main/delete_returning.result index 3a95de0cdca..ab795149de7 100644 --- a/mysql-test/main/delete_returning.result +++ b/mysql-test/main/delete_returning.result @@ -211,3 +211,19 @@ id 3 set sql_mode=@sql_mode_save; DROP TABLE t1; +# +# MDEV-3953 Add columns for ROWS_EXAMINED, ROWS_SENT, and ROWS_READ to I_S and +# processlist +# +create table t1 (a int primary key, b int); +insert into t1 select seq,seq+1 from seq_1_to_10; +flush status; +delete from t1 where a between 1 and 3 returning a,b; +a b +1 2 +2 3 +3 4 +show status like "Rows_sent"; +Variable_name Value +Rows_sent 3 +drop table t1; diff --git a/mysql-test/main/delete_returning.test b/mysql-test/main/delete_returning.test index 4448a6bcccd..cdfb48e843f 100644 --- a/mysql-test/main/delete_returning.test +++ b/mysql-test/main/delete_returning.test @@ -1,3 +1,4 @@ +--source include/have_sequence.inc # # Tests for DELETE FROM ... RETURNING ,... # @@ -170,3 +171,15 @@ DELETE FROM t1 WHERE id > 2 RETURNING *; set sql_mode=@sql_mode_save; DROP TABLE t1; + +--echo # +--echo # MDEV-3953 Add columns for ROWS_EXAMINED, ROWS_SENT, and ROWS_READ to I_S and +--echo # processlist +--echo # + +create table t1 (a int primary key, b int); +insert into t1 select seq,seq+1 from seq_1_to_10; +flush status; +delete from t1 where a between 1 and 3 returning a,b; +show status like "Rows_sent"; +drop table t1; diff --git a/mysql-test/main/func_compress.test b/mysql-test/main/func_compress.test index f41a5898154..221dddd59f5 100644 --- a/mysql-test/main/func_compress.test +++ b/mysql-test/main/func_compress.test @@ -1,4 +1,5 @@ -- source include/have_compress.inc +-- source include/have_normal_bzip.inc # # Test for compress and uncompress functions: # diff --git a/mysql-test/main/func_debug.result b/mysql-test/main/func_debug.result index c8efcf09d41..37f2a19fc6c 100644 --- a/mysql-test/main/func_debug.result +++ b/mysql-test/main/func_debug.result @@ -912,7 +912,8 @@ a IN (CAST(1 AS SIGNED), CAST(1 AS UNSIGNED)) Warnings: Note 1105 DBUG: [0] arg=1 handler=0 (bigint) Note 1105 DBUG: [1] arg=2 handler=1 (decimal) -Note 1105 DBUG: types_compatible=no bisect=no +Note 1105 DBUG: found a mix of UINT and SINT +Note 1105 DBUG: types_compatible=yes bisect=yes SELECT a IN (CAST(1 AS SIGNED), CAST(1 AS UNSIGNED),NULL) FROM t1; a IN (CAST(1 AS SIGNED), CAST(1 AS UNSIGNED),NULL) Warnings: @@ -950,7 +951,8 @@ a NOT IN (CAST(1 AS SIGNED), CAST(1 AS UNSIGNED)) Warnings: Note 1105 DBUG: [0] arg=1 handler=0 (bigint) Note 1105 DBUG: [1] arg=2 handler=1 (decimal) -Note 1105 DBUG: types_compatible=no bisect=no +Note 1105 DBUG: found a mix of UINT and SINT +Note 1105 DBUG: types_compatible=yes bisect=yes SELECT a NOT IN (CAST(1 AS SIGNED), CAST(1 AS UNSIGNED),NULL) FROM t1; a NOT IN (CAST(1 AS SIGNED), CAST(1 AS UNSIGNED),NULL) Warnings: @@ -1624,7 +1626,8 @@ a b Warnings: Note 1105 DBUG: [0] arg=1 handler=0 (bigint) Note 1105 DBUG: [1] arg=2 handler=1 (decimal) -Note 1105 DBUG: types_compatible=no bisect=no +Note 1105 DBUG: found a mix of UINT and SINT +Note 1105 DBUG: types_compatible=yes bisect=no DROP TABLE t1; # # MDEV-11554 Wrong result for CASE on a mixture of signed and unsigned expressions diff --git a/mysql-test/main/func_in.result b/mysql-test/main/func_in.result index 175e23ec65f..4627208d79f 100644 --- a/mysql-test/main/func_in.result +++ b/mysql-test/main/func_in.result @@ -935,6 +935,43 @@ Warning 1292 Truncated incorrect DECIMAL value: '0x' # End of 10.4 tests # # +# Start of 10.5 tests +# +# +# MDEV-31303: Key not used +# +CREATE TABLE `a` ( +`id` bigint AUTO_INCREMENT PRIMARY KEY, +`c1` bigint unsigned, +KEY (`c1`) +); +INSERT INTO `a` VALUES (1,9223382399205928659),(2,9223384207280813348), +(3,9223385953115437234),(4,9223387250780556749),(5,9223387354282558788), +(6,9223387603870501596),(7,9223389270813433667),(8,9223389903231468827), +(9,9223390280789586779),(10,9223391591398222899),(11,9223391875473564350), +(12,9223393152250049433),(13,9223393939696790223),(14,9223394417225350415), +(15,9223397646397141015),(16,9223398025879291243),(17,9223399038671098072), +(18,9223399534968874556),(19,9223400449518009285),(20,9223400860292643549), +(21,9223400940692256924),(22,9223401073791948119),(23,9223402820804649616), +(24,9223403470951992681),(25,9223405581879567267),(26,9223405754978563829), +(27,9223405972966828221), (28, 9223372036854775808), (29, 9223372036854775807) ; +explain SELECT c1 FROM a WHERE c1 IN ( 1, 9223372036854775807 ); +id select_type table type possible_keys key key_len ref rows Extra +1 SIMPLE a range c1 c1 9 NULL 2 Using where; Using index +explain SELECT c1 FROM a WHERE c1 IN ( 1, 9223372036854775808 ); +id select_type table type possible_keys key key_len ref rows Extra +1 SIMPLE a range c1 c1 9 NULL 2 Using where; Using index +SELECT c1 FROM a WHERE c1 IN ( 1, 9223372036854775807 ); +c1 +9223372036854775807 +SELECT c1 FROM a WHERE c1 IN ( 1, 9223372036854775808 ); +c1 +9223372036854775808 +drop table `a`; +# +# End of 10.5 tests +# +# # MDEV-29662 same values in `IN` set vs equal comparison produces # the different performance # diff --git a/mysql-test/main/func_in.test b/mysql-test/main/func_in.test index 847c48d31a9..e39932a2d50 100644 --- a/mysql-test/main/func_in.test +++ b/mysql-test/main/func_in.test @@ -712,6 +712,40 @@ SELECT ('0x',1) IN ((0,1),(1,1)); --echo # End of 10.4 tests --echo # +--echo # +--echo # Start of 10.5 tests +--echo # + +--echo # +--echo # MDEV-31303: Key not used +--echo # +CREATE TABLE `a` ( + `id` bigint AUTO_INCREMENT PRIMARY KEY, + `c1` bigint unsigned, + KEY (`c1`) +); + +INSERT INTO `a` VALUES (1,9223382399205928659),(2,9223384207280813348), +(3,9223385953115437234),(4,9223387250780556749),(5,9223387354282558788), +(6,9223387603870501596),(7,9223389270813433667),(8,9223389903231468827), +(9,9223390280789586779),(10,9223391591398222899),(11,9223391875473564350), +(12,9223393152250049433),(13,9223393939696790223),(14,9223394417225350415), +(15,9223397646397141015),(16,9223398025879291243),(17,9223399038671098072), +(18,9223399534968874556),(19,9223400449518009285),(20,9223400860292643549), +(21,9223400940692256924),(22,9223401073791948119),(23,9223402820804649616), +(24,9223403470951992681),(25,9223405581879567267),(26,9223405754978563829), +(27,9223405972966828221), (28, 9223372036854775808), (29, 9223372036854775807) ; + +explain SELECT c1 FROM a WHERE c1 IN ( 1, 9223372036854775807 ); +explain SELECT c1 FROM a WHERE c1 IN ( 1, 9223372036854775808 ); +SELECT c1 FROM a WHERE c1 IN ( 1, 9223372036854775807 ); +SELECT c1 FROM a WHERE c1 IN ( 1, 9223372036854775808 ); +drop table `a`; + +--echo # +--echo # End of 10.5 tests +--echo # + --echo # --echo # MDEV-29662 same values in `IN` set vs equal comparison produces --echo # the different performance @@ -845,4 +879,3 @@ drop table t1; --echo # --echo # End of 10.6 tests --echo # - diff --git a/mysql-test/main/grant.result b/mysql-test/main/grant.result index 9d95f2fa478..cedaf10b3f6 100644 --- a/mysql-test/main/grant.result +++ b/mysql-test/main/grant.result @@ -225,7 +225,7 @@ revoke LOCK TABLES, ALTER on mysqltest.* from mysqltest_1@localhost; show grants for mysqltest_1@localhost; Grants for mysqltest_1@localhost GRANT USAGE ON *.* TO `mysqltest_1`@`localhost` -GRANT SELECT, INSERT, UPDATE, DELETE, CREATE, DROP, REFERENCES, INDEX, CREATE TEMPORARY TABLES, EXECUTE, CREATE VIEW, SHOW VIEW, CREATE ROUTINE, ALTER ROUTINE, EVENT, TRIGGER, DELETE HISTORY ON `mysqltest`.* TO `mysqltest_1`@`localhost` WITH GRANT OPTION +GRANT SELECT, INSERT, UPDATE, DELETE, CREATE, DROP, REFERENCES, INDEX, CREATE TEMPORARY TABLES, EXECUTE, CREATE VIEW, SHOW VIEW, CREATE ROUTINE, ALTER ROUTINE, EVENT, TRIGGER, DELETE HISTORY, SHOW CREATE ROUTINE ON `mysqltest`.* TO `mysqltest_1`@`localhost` WITH GRANT OPTION revoke all privileges on mysqltest.* from mysqltest_1@localhost; delete from mysql.user where user='mysqltest_1'; flush privileges; @@ -639,6 +639,7 @@ Federated admin Server To execute the CREATE SERVER, ALTER SERVER, DROP SERVER s Connection admin Server To bypass connection limits and kill other users' connections Read_only admin Server To perform write operations even if @@read_only=ON Usage Server Admin No privileges - allow connect only +Show Create Routine Databases,Functions,Procedures To allow SHOW CREATE PROCEDURE/FUNCTION/PACKAGE connect root,localhost,root,,test,$MASTER_MYPORT,$MASTER_MYSOCK; connection root; create database mysqltest; @@ -776,7 +777,7 @@ flush privileges; use test; set @user123="non-existent"; select * from mysql.db where user=@user123; -Host Db User Select_priv Insert_priv Update_priv Delete_priv Create_priv Drop_priv Grant_priv References_priv Index_priv Alter_priv Create_tmp_table_priv Lock_tables_priv Create_view_priv Show_view_priv Create_routine_priv Alter_routine_priv Execute_priv Event_priv Trigger_priv Delete_history_priv +Host Db User Select_priv Insert_priv Update_priv Delete_priv Create_priv Drop_priv Grant_priv References_priv Index_priv Alter_priv Create_tmp_table_priv Lock_tables_priv Create_view_priv Show_view_priv Create_routine_priv Alter_routine_priv Execute_priv Event_priv Trigger_priv Delete_history_priv Show_create_routine_priv set names koi8r; create database ÂÄ; grant select on ÂÄ.* to root@localhost; @@ -2841,11 +2842,11 @@ CREATE USER ten2; GRANT ALL ON *.* TO ten2; SHOW GRANTS FOR ten2; Grants for ten2@% -GRANT ALL PRIVILEGES ON *.* TO `ten2`@`%` +GRANT SELECT, INSERT, UPDATE, DELETE, CREATE, DROP, RELOAD, SHUTDOWN, PROCESS, FILE, REFERENCES, INDEX, ALTER, SHOW DATABASES, SUPER, CREATE TEMPORARY TABLES, LOCK TABLES, EXECUTE, REPLICATION SLAVE, BINLOG MONITOR, CREATE VIEW, SHOW VIEW, CREATE ROUTINE, ALTER ROUTINE, CREATE USER, EVENT, TRIGGER, CREATE TABLESPACE, DELETE HISTORY, SET USER, FEDERATED ADMIN, CONNECTION ADMIN, READ_ONLY ADMIN, REPLICATION SLAVE ADMIN, REPLICATION MASTER ADMIN, BINLOG ADMIN, BINLOG REPLAY, SLAVE MONITOR ON *.* TO `ten2`@`%` FLUSH PRIVILEGES; SHOW GRANTS FOR ten2; Grants for ten2@% -GRANT ALL PRIVILEGES ON *.* TO `ten2`@`%` +GRANT SELECT, INSERT, UPDATE, DELETE, CREATE, DROP, RELOAD, SHUTDOWN, PROCESS, FILE, REFERENCES, INDEX, ALTER, SHOW DATABASES, SUPER, CREATE TEMPORARY TABLES, LOCK TABLES, EXECUTE, REPLICATION SLAVE, BINLOG MONITOR, CREATE VIEW, SHOW VIEW, CREATE ROUTINE, ALTER ROUTINE, CREATE USER, EVENT, TRIGGER, CREATE TABLESPACE, DELETE HISTORY, SET USER, FEDERATED ADMIN, CONNECTION ADMIN, READ_ONLY ADMIN, REPLICATION SLAVE ADMIN, REPLICATION MASTER ADMIN, BINLOG ADMIN, BINLOG REPLAY, SLAVE MONITOR ON *.* TO `ten2`@`%` DROP USER ten2; # switching back from mysql.user to mysql.global_priv # diff --git a/mysql-test/main/grant_slave_monitor.result b/mysql-test/main/grant_slave_monitor.result index 78f6b23b1ff..8dd90f1183e 100644 --- a/mysql-test/main/grant_slave_monitor.result +++ b/mysql-test/main/grant_slave_monitor.result @@ -6,7 +6,7 @@ connect con1,localhost,user1,,; connection con1; SHOW GRANTS; Grants for user1@localhost -GRANT SELECT, INSERT, UPDATE, DELETE, CREATE, DROP, RELOAD, SHUTDOWN, PROCESS, FILE, REFERENCES, INDEX, ALTER, SHOW DATABASES, SUPER, CREATE TEMPORARY TABLES, LOCK TABLES, EXECUTE, REPLICATION SLAVE, BINLOG MONITOR, CREATE VIEW, SHOW VIEW, CREATE ROUTINE, ALTER ROUTINE, CREATE USER, EVENT, TRIGGER, CREATE TABLESPACE, DELETE HISTORY, SET USER, FEDERATED ADMIN, CONNECTION ADMIN, READ_ONLY ADMIN, REPLICATION SLAVE ADMIN, REPLICATION MASTER ADMIN, BINLOG ADMIN, BINLOG REPLAY ON *.* TO `user1`@`localhost` +GRANT SELECT, INSERT, UPDATE, DELETE, CREATE, DROP, RELOAD, SHUTDOWN, PROCESS, FILE, REFERENCES, INDEX, ALTER, SHOW DATABASES, SUPER, CREATE TEMPORARY TABLES, LOCK TABLES, EXECUTE, REPLICATION SLAVE, BINLOG MONITOR, CREATE VIEW, SHOW VIEW, CREATE ROUTINE, ALTER ROUTINE, CREATE USER, EVENT, TRIGGER, CREATE TABLESPACE, DELETE HISTORY, SET USER, FEDERATED ADMIN, CONNECTION ADMIN, READ_ONLY ADMIN, REPLICATION SLAVE ADMIN, REPLICATION MASTER ADMIN, BINLOG ADMIN, BINLOG REPLAY, SHOW CREATE ROUTINE ON *.* TO `user1`@`localhost` # # Verify that having REPLICATION SLAVE ADMIN doesn't allow SHOW SLAVE STATUS # Expected error: Access denied; you need (at least one of) the SLAVE MONITOR privilege(s) for this operation @@ -46,13 +46,13 @@ insert mysql.global_priv values ('bar', 'foo7', '{"access":274877906943,"version flush privileges; show grants for foo7@bar; Grants for foo7@bar -GRANT ALL PRIVILEGES ON *.* TO `foo7`@`bar` WITH GRANT OPTION +GRANT SELECT, INSERT, UPDATE, DELETE, CREATE, DROP, RELOAD, SHUTDOWN, PROCESS, FILE, REFERENCES, INDEX, ALTER, SHOW DATABASES, SUPER, CREATE TEMPORARY TABLES, LOCK TABLES, EXECUTE, REPLICATION SLAVE, BINLOG MONITOR, CREATE VIEW, SHOW VIEW, CREATE ROUTINE, ALTER ROUTINE, CREATE USER, EVENT, TRIGGER, CREATE TABLESPACE, DELETE HISTORY, SET USER, FEDERATED ADMIN, CONNECTION ADMIN, READ_ONLY ADMIN, REPLICATION SLAVE ADMIN, REPLICATION MASTER ADMIN, BINLOG ADMIN, BINLOG REPLAY, SLAVE MONITOR ON *.* TO `foo7`@`bar` WITH GRANT OPTION show grants for foo8@bar; Grants for foo8@bar -GRANT ALL PRIVILEGES ON *.* TO `foo8`@`bar` WITH GRANT OPTION +GRANT SELECT, INSERT, UPDATE, DELETE, CREATE, DROP, RELOAD, SHUTDOWN, PROCESS, FILE, REFERENCES, INDEX, ALTER, SHOW DATABASES, SUPER, CREATE TEMPORARY TABLES, LOCK TABLES, EXECUTE, REPLICATION SLAVE, BINLOG MONITOR, CREATE VIEW, SHOW VIEW, CREATE ROUTINE, ALTER ROUTINE, CREATE USER, EVENT, TRIGGER, CREATE TABLESPACE, DELETE HISTORY, SET USER, FEDERATED ADMIN, CONNECTION ADMIN, READ_ONLY ADMIN, REPLICATION SLAVE ADMIN, REPLICATION MASTER ADMIN, BINLOG ADMIN, BINLOG REPLAY, SLAVE MONITOR ON *.* TO `foo8`@`bar` WITH GRANT OPTION show grants for foo9@bar; Grants for foo9@bar -GRANT ALL PRIVILEGES ON *.* TO `foo9`@`bar` WITH GRANT OPTION +GRANT SELECT, INSERT, UPDATE, DELETE, CREATE, DROP, RELOAD, SHUTDOWN, PROCESS, FILE, REFERENCES, INDEX, ALTER, SHOW DATABASES, SUPER, CREATE TEMPORARY TABLES, LOCK TABLES, EXECUTE, REPLICATION SLAVE, BINLOG MONITOR, CREATE VIEW, SHOW VIEW, CREATE ROUTINE, ALTER ROUTINE, CREATE USER, EVENT, TRIGGER, CREATE TABLESPACE, DELETE HISTORY, SET USER, FEDERATED ADMIN, CONNECTION ADMIN, READ_ONLY ADMIN, REPLICATION SLAVE ADMIN, REPLICATION MASTER ADMIN, BINLOG ADMIN, BINLOG REPLAY, SLAVE MONITOR ON *.* TO `foo9`@`bar` WITH GRANT OPTION drop user foo7@bar, foo8@bar, foo9@bar; # # End of 10.5 tests diff --git a/mysql-test/main/having.result b/mysql-test/main/having.result index d7cbadd5e75..bcb71b644c5 100644 --- a/mysql-test/main/having.result +++ b/mysql-test/main/having.result @@ -906,5 +906,54 @@ SELECT * FROM t HAVING f = 'foo'; f DROP TABLE t; # +# MDEV-29731 Crash when HAVING in a correlated subquery references +# columns in the outer query +# +CREATE TABLE t (a INT, b INT); +SELECT 1 FROM t +WHERE b = (SELECT 1 FROM t GROUP BY a HAVING b = a+1); +1 +DROP TABLE t; +CREATE TABLE t (a INT, b INT, c INT); +SELECT 1 FROM t +WHERE (b,c) = (SELECT 1,1 FROM t GROUP BY a HAVING b = a+1 and c = a-1); +1 +DROP TABLE t; +CREATE TABLE t (a TEXT, b INT UNIQUE); +SELECT 1 FROM t +WHERE b IN (SELECT 1 FROM t +GROUP BY '', a +HAVING (CASE b WHEN 1 +'' THEN 3 ELSE a END) +ORDER BY b) +GROUP BY b HAVING b = 1; +1 +Warnings: +Warning 1292 Truncated incorrect DOUBLE value: '' +DROP TABLE t; +CREATE TABLE t (a INT, b CHAR KEY UNIQUE); +CREATE VIEW v AS SELECT * FROM t WHERE a LIKE '' GROUP BY b HAVING a > a; +SELECT * FROM v AS v1 NATURAL JOIN v AS v5 NATURAL JOIN v +WHERE a LIKE '' AND b IN (SELECT a FROM t +WHERE a LIKE '' + GROUP BY a +HAVING b LIKE (b < +1 OR a > 1) >= b); +a b +DROP VIEW v; +DROP TABLE t; +EXECUTE IMMEDIATE 'SELECT LEAD(c) OVER (ORDER BY c) + FROM (SELECT 0 AS c) AS a NATURAL JOIN (SELECT 0 AS c) AS b;'; +LEAD(c) OVER (ORDER BY c) +NULL +CREATE TABLE t (a INT); +UPDATE t SET a = '' + WHERE 1 IN (SELECT * FROM +(SELECT * FROM +(SELECT * FROM t AS v5 NATURAL JOIN t AS v4 NATURAL JOIN t) AS v3 +NATURAL JOIN t +GROUP BY a) AS v2 +WHERE (0, a) IN ((0,-1),(+1,0)) +ORDER BY 1+AVG(a) OVER (ORDER BY a)) ORDER BY a; +DROP TABLE t; +# # End of 10.4 tests # diff --git a/mysql-test/main/having.test b/mysql-test/main/having.test index 397b220978e..7b8e72cfe1d 100644 --- a/mysql-test/main/having.test +++ b/mysql-test/main/having.test @@ -950,8 +950,53 @@ DROP TABLE t1,t2; CREATE TABLE t (f VARCHAR(512)); INSERT INTO t VALUES ('a'),('b'); SELECT * FROM t HAVING f = 'foo'; +DROP TABLE t; -# Cleanup +--echo # +--echo # MDEV-29731 Crash when HAVING in a correlated subquery references +--echo # columns in the outer query +--echo # +CREATE TABLE t (a INT, b INT); +SELECT 1 FROM t + WHERE b = (SELECT 1 FROM t GROUP BY a HAVING b = a+1); +DROP TABLE t; + +CREATE TABLE t (a INT, b INT, c INT); +SELECT 1 FROM t + WHERE (b,c) = (SELECT 1,1 FROM t GROUP BY a HAVING b = a+1 and c = a-1); +DROP TABLE t; + +CREATE TABLE t (a TEXT, b INT UNIQUE); +SELECT 1 FROM t + WHERE b IN (SELECT 1 FROM t + GROUP BY '', a + HAVING (CASE b WHEN 1 +'' THEN 3 ELSE a END) + ORDER BY b) + GROUP BY b HAVING b = 1; +DROP TABLE t; + +CREATE TABLE t (a INT, b CHAR KEY UNIQUE); +CREATE VIEW v AS SELECT * FROM t WHERE a LIKE '' GROUP BY b HAVING a > a; +SELECT * FROM v AS v1 NATURAL JOIN v AS v5 NATURAL JOIN v + WHERE a LIKE '' AND b IN (SELECT a FROM t + WHERE a LIKE '' + GROUP BY a + HAVING b LIKE (b < +1 OR a > 1) >= b); +DROP VIEW v; +DROP TABLE t; + +EXECUTE IMMEDIATE 'SELECT LEAD(c) OVER (ORDER BY c) + FROM (SELECT 0 AS c) AS a NATURAL JOIN (SELECT 0 AS c) AS b;'; + +CREATE TABLE t (a INT); +UPDATE t SET a = '' + WHERE 1 IN (SELECT * FROM + (SELECT * FROM + (SELECT * FROM t AS v5 NATURAL JOIN t AS v4 NATURAL JOIN t) AS v3 + NATURAL JOIN t + GROUP BY a) AS v2 + WHERE (0, a) IN ((0,-1),(+1,0)) + ORDER BY 1+AVG(a) OVER (ORDER BY a)) ORDER BY a; DROP TABLE t; --echo # diff --git a/mysql-test/main/information_schema.result b/mysql-test/main/information_schema.result index a00b8790ee0..154f60ae35c 100644 --- a/mysql-test/main/information_schema.result +++ b/mysql-test/main/information_schema.result @@ -389,21 +389,32 @@ connect user2,localhost,mysqltest_1,,; connection user2; select ROUTINE_NAME, ROUTINE_DEFINITION from information_schema.ROUTINES WHERE ROUTINE_SCHEMA <> 'sys'; ROUTINE_NAME ROUTINE_DEFINITION -sel2 NULL -sub1 NULL +sel2 begin +select * from t1; +select * from t2; +end +sub1 return i+1 create function sub2(i int) returns int return i+1; select ROUTINE_NAME, ROUTINE_DEFINITION from information_schema.ROUTINES WHERE ROUTINE_SCHEMA <> 'sys'; ROUTINE_NAME ROUTINE_DEFINITION -sel2 NULL -sub1 NULL +sel2 begin +select * from t1; +select * from t2; +end +sub1 return i+1 sub2 return i+1 show create procedure sel2; Procedure sql_mode Create Procedure character_set_client collation_connection Database Collation -sel2 NULL latin1 latin1_swedish_ci latin1_swedish_ci +sel2 CREATE DEFINER=`root`@`localhost` PROCEDURE `sel2`() +begin +select * from t1; +select * from t2; +end latin1 latin1_swedish_ci latin1_swedish_ci show create function sub1; Function sql_mode Create Function character_set_client collation_connection Database Collation -sub1 NULL latin1 latin1_swedish_ci latin1_swedish_ci +sub1 CREATE DEFINER=`root`@`localhost` FUNCTION `sub1`(i int) RETURNS int(11) +return i+1 latin1 latin1_swedish_ci latin1_swedish_ci show create function sub2; Function sql_mode Create Function character_set_client collation_connection Database Collation sub2 CREATE DEFINER=`mysqltest_1`@`localhost` FUNCTION `sub2`(i int) RETURNS int(11) @@ -501,6 +512,7 @@ GRANTEE TABLE_CATALOG TABLE_SCHEMA PRIVILEGE_TYPE IS_GRANTABLE 'mysqltest_1'@'localhost' def test EVENT YES 'mysqltest_1'@'localhost' def test TRIGGER YES 'mysqltest_1'@'localhost' def test DELETE HISTORY YES +'mysqltest_1'@'localhost' def test SHOW CREATE ROUTINE YES select * from information_schema.TABLE_PRIVILEGES where grantee like '%mysqltest_1%'; GRANTEE TABLE_CATALOG TABLE_SCHEMA TABLE_NAME PRIVILEGE_TYPE IS_GRANTABLE 'mysqltest_1'@'localhost' def test t1 SELECT NO diff --git a/mysql-test/main/insert_returning.result b/mysql-test/main/insert_returning.result index b2ed9c90e51..c58e1c66378 100644 --- a/mysql-test/main/insert_returning.result +++ b/mysql-test/main/insert_returning.result @@ -683,3 +683,23 @@ INSERT t WITH cte AS (SELECT 1) SELECT * FROM cte RETURNING *; a 1 DROP TABLE t; +# +# MDEV-3953 Add columns for ROWS_EXAMINED, ROWS_SENT, and ROWS_READ to I_S and +# processlist +# +create table t1 (a int primary key, b int); +flush status; +insert into t1 values (1,2),(2,4) returning a,b; +a b +1 2 +2 4 +insert into t1 select seq,seq from seq_10_to_13 returning a,b; +a b +10 10 +11 11 +12 12 +13 13 +show status like "Rows_sent"; +Variable_name Value +Rows_sent 6 +drop table t1; diff --git a/mysql-test/main/insert_returning.test b/mysql-test/main/insert_returning.test index 837d61d2c16..250ca55024f 100644 --- a/mysql-test/main/insert_returning.test +++ b/mysql-test/main/insert_returning.test @@ -1,3 +1,5 @@ +--source include/have_sequence.inc + --echo # Test for INSERT...RETURNING CREATE TABLE t1(id1 INT PRIMARY KEY AUTO_INCREMENT, val1 VARCHAR(1)); @@ -396,3 +398,15 @@ CREATE TABLE t (a INT); INSERT t WITH cte AS (SELECT 1) SELECT * FROM cte RETURNING *; DROP TABLE t; + +--echo # +--echo # MDEV-3953 Add columns for ROWS_EXAMINED, ROWS_SENT, and ROWS_READ to I_S and +--echo # processlist +--echo # + +create table t1 (a int primary key, b int); +flush status; +insert into t1 values (1,2),(2,4) returning a,b; +insert into t1 select seq,seq from seq_10_to_13 returning a,b; +show status like "Rows_sent"; +drop table t1; diff --git a/mysql-test/main/join_outer.result b/mysql-test/main/join_outer.result index ce9dbfb8c3d..c4ea5bc4517 100644 --- a/mysql-test/main/join_outer.result +++ b/mysql-test/main/join_outer.result @@ -1804,7 +1804,7 @@ sum(t3.b) show status like "handler_read%"; Variable_name Value Handler_read_first 0 -Handler_read_key 13 +Handler_read_key 4 Handler_read_last 0 Handler_read_next 5 Handler_read_prev 0 @@ -1819,7 +1819,7 @@ sum(t3.b) show status like "handler_read%"; Variable_name Value Handler_read_first 0 -Handler_read_key 7 +Handler_read_key 4 Handler_read_last 0 Handler_read_next 5 Handler_read_prev 0 diff --git a/mysql-test/main/join_outer_jcl6.result b/mysql-test/main/join_outer_jcl6.result index a34bf96a0ef..bdaab88e01f 100644 --- a/mysql-test/main/join_outer_jcl6.result +++ b/mysql-test/main/join_outer_jcl6.result @@ -1811,7 +1811,7 @@ sum(t3.b) show status like "handler_read%"; Variable_name Value Handler_read_first 0 -Handler_read_key 13 +Handler_read_key 4 Handler_read_last 0 Handler_read_next 5 Handler_read_prev 0 @@ -1826,7 +1826,7 @@ sum(t3.b) show status like "handler_read%"; Variable_name Value Handler_read_first 0 -Handler_read_key 7 +Handler_read_key 4 Handler_read_last 0 Handler_read_next 5 Handler_read_prev 0 diff --git a/mysql-test/main/log_slow.result b/mysql-test/main/log_slow.result index 8f2d3194a27..b236288b0bf 100644 --- a/mysql-test/main/log_slow.result +++ b/mysql-test/main/log_slow.result @@ -13,6 +13,7 @@ Variable_name Value log_slow_admin_statements ON log_slow_disabled_statements sp log_slow_filter admin,filesort,filesort_on_disk,filesort_priority_queue,full_join,full_scan,query_cache,query_cache_miss,tmp_table,tmp_table_on_disk +log_slow_max_warnings 10 log_slow_min_examined_row_limit 0 log_slow_query ON log_slow_query_file $PATH/mysqld-slow.log @@ -56,15 +57,15 @@ start_time timestamp(6) NO current_timestamp(6) on update current_timestamp(6) user_host mediumtext NO NULL query_time time(6) NO NULL lock_time time(6) NO NULL -rows_sent int(11) NO NULL -rows_examined int(11) NO NULL +rows_sent bigint(20) unsigned NO NULL +rows_examined bigint(20) unsigned NO NULL db varchar(512) NO NULL last_insert_id int(11) NO NULL insert_id int(11) NO NULL server_id int(10) unsigned NO NULL sql_text mediumtext NO NULL thread_id bigint(21) unsigned NO NULL -rows_affected int(11) NO NULL +rows_affected bigint(20) unsigned NO NULL flush slow logs; set long_query_time=0.1; set log_slow_filter=''; @@ -137,3 +138,54 @@ drop table t; # # End of 10.3 tests # +# +# MDEV-31742: incorrect examined rows in case of stored function usage +# +CREATE TABLE `tab_MDEV_30820` ( +`ID` int(11) NOT NULL AUTO_INCREMENT, +`NAME_F` varchar(50) DEFAULT NULL, +PRIMARY KEY (`ID`) +); +CREATE TABLE `tab2` ( +`ID` int(11) NOT NULL AUTO_INCREMENT, +`TAB1_ID` int(11) DEFAULT NULL, +PRIMARY KEY (`id`) +); +CREATE FUNCTION `get_zero`() RETURNS int(11) +BEGIN +RETURN(0) ; +END +// +for i in 1..100 do insert into tab_MDEV_30820 values (i,'qwerty'); end for ; // +for i in 1..1000 do insert into tab2 values (i,i+300); end for ; // +SET @old_slow_query_log= @@global.slow_query_log; +SET @old_log_output= @@global.log_output; +SET @old_long_query_time= @@long_query_time; +SET GLOBAL log_output= "TABLE"; +SET GLOBAL slow_query_log= ON; +SET SESSION slow_query_log=ON; +SET SESSION long_query_time= 0; +SELECT 0 as zero, (SELECT ID FROM tab2 where tab2.TAB1_ID = +tab_MDEV_30820.ID ORDER BY 1 LIMIT 1 ) AS F1 FROM tab_MDEV_30820 ORDER BY 2 DESC LIMIT 2; +zero F1 +0 NULL +0 NULL +SELECT get_zero() as zero, (SELECT ID FROM tab2 where tab2.TAB1_ID = +tab_MDEV_30820.ID ORDER BY 1 LIMIT 1) AS F1 FROM tab_MDEV_30820 ORDER BY 2 DESC LIMIT 2; +zero F1 +0 NULL +0 NULL +# should be the same rows_examined +SELECT rows_examined FROM mysql.slow_log WHERE sql_text LIKE '%SELECT%tab_MDEV_30820%'; +rows_examined +100202 +100202 +SET @@long_query_time= @old_long_query_time; +SET @@global.log_output= @old_log_output; +SET @@global.slow_query_log= @old_slow_query_log; +SET SESSION slow_query_log=default; +drop table tab_MDEV_30820, tab2; +drop function get_zero; +# +# End of 10.4 tests +# diff --git a/mysql-test/main/log_slow.test b/mysql-test/main/log_slow.test index 65da292b7dd..ea8b9127658 100644 --- a/mysql-test/main/log_slow.test +++ b/mysql-test/main/log_slow.test @@ -122,3 +122,70 @@ drop table t; --echo # --echo # End of 10.3 tests --echo # + + +--echo # +--echo # MDEV-31742: incorrect examined rows in case of stored function usage +--echo # + + +CREATE TABLE `tab_MDEV_30820` ( +`ID` int(11) NOT NULL AUTO_INCREMENT, +`NAME_F` varchar(50) DEFAULT NULL, + PRIMARY KEY (`ID`) +); + + CREATE TABLE `tab2` ( + `ID` int(11) NOT NULL AUTO_INCREMENT, + `TAB1_ID` int(11) DEFAULT NULL, + PRIMARY KEY (`id`) +); + +--disable_ps2_protocol +--disable_view_protocol + +--delimiter // +CREATE FUNCTION `get_zero`() RETURNS int(11) +BEGIN + RETURN(0) ; +END +// + +for i in 1..100 do insert into tab_MDEV_30820 values (i,'qwerty'); end for ; // +for i in 1..1000 do insert into tab2 values (i,i+300); end for ; // + +--delimiter ; + +SET @old_slow_query_log= @@global.slow_query_log; +SET @old_log_output= @@global.log_output; +SET @old_long_query_time= @@long_query_time; +SET GLOBAL log_output= "TABLE"; +SET GLOBAL slow_query_log= ON; + +SET SESSION slow_query_log=ON; +SET SESSION long_query_time= 0; + +SELECT 0 as zero, (SELECT ID FROM tab2 where tab2.TAB1_ID = +tab_MDEV_30820.ID ORDER BY 1 LIMIT 1 ) AS F1 FROM tab_MDEV_30820 ORDER BY 2 DESC LIMIT 2; + +SELECT get_zero() as zero, (SELECT ID FROM tab2 where tab2.TAB1_ID = +tab_MDEV_30820.ID ORDER BY 1 LIMIT 1) AS F1 FROM tab_MDEV_30820 ORDER BY 2 DESC LIMIT 2; + +--echo # should be the same rows_examined +SELECT rows_examined FROM mysql.slow_log WHERE sql_text LIKE '%SELECT%tab_MDEV_30820%'; + +## Reset to initial values +SET @@long_query_time= @old_long_query_time; +SET @@global.log_output= @old_log_output; +SET @@global.slow_query_log= @old_slow_query_log; +SET SESSION slow_query_log=default; + +drop table tab_MDEV_30820, tab2; +drop function get_zero; + +--enable_view_protocol +--enable_ps2_protocol + +--echo # +--echo # End of 10.4 tests +--echo # diff --git a/mysql-test/main/log_slow_debug.result b/mysql-test/main/log_slow_debug.result index eaf38425f8b..5f4f4c6a059 100644 --- a/mysql-test/main/log_slow_debug.result +++ b/mysql-test/main/log_slow_debug.result @@ -230,6 +230,91 @@ sql_text [slow] DEALLOCATE PREPARE stmt [slow] DROP SEQUENCE s4 # +# Start of 10.6 tests +# +# +# MDEV-32203 Raise notes when an index cannot be used on data type +# mismatch +# +CREATE TABLE t1 (a VARCHAR(10), KEY(a)); +insert into t1 select seq from seq_0_to_31; +SET note_verbosity=all; +SET log_slow_verbosity=all; +SET global log_output='FILE'; +set @org_slow_query_log_file=@@global.slow_query_log_file; +set global slow_query_log_file='MYSQLTEST_VARDIR/tmp/log_slow_debug-1.log'; +FLUSH SLOW LOGS; +SELECT * FROM t1 WHERE a=10; +a +10 +Warnings: +Note 1105 Cannot use key `a` part[0] for lookup: `test`.`t1`.`a` of type `varchar` = "10" of type `int` +EXPLAIN SELECT * FROM t1 WHERE a=10; +id select_type table type possible_keys key key_len ref rows Extra +1 SIMPLE t1 index a a 13 NULL 32 Using where; Using index +Warnings: +Note 1105 Cannot use key `a` part[0] for lookup: `test`.`t1`.`a` of type `varchar` = "10" of type `int` +FOUND 2 /# Warnings/ in log_slow_debug-1.log +FOUND 1 /# Note.*Cannot use key.*varchar.*10.*int/ in log_slow_debug-1.log +set global slow_query_log_file='MYSQLTEST_VARDIR/tmp/log_slow_debug-2.log'; +SET note_verbosity="explain"; +FLUSH SLOW LOGS; +EXPLAIN SELECT * FROM t1 WHERE a=10; +id select_type table type possible_keys key key_len ref rows Extra +1 SIMPLE t1 index a a 13 NULL 32 Using where; Using index +Warnings: +Note 1105 Cannot use key `a` part[0] for lookup: `test`.`t1`.`a` of type `varchar` = "10" of type `int` +FOUND 1 /# Warnings/ in log_slow_debug-2.log +FOUND 1 /# Note.*Cannot use key.*varchar.*10.*int/ in log_slow_debug-2.log +set global slow_query_log_file='MYSQLTEST_VARDIR/tmp/log_slow_debug-3.log'; +SET log_slow_verbosity=replace(@@log_slow_verbosity, "warnings", ""); +SET log_slow_verbosity=replace(@@log_slow_verbosity, "full", ""); +SET note_verbosity=all; +FLUSH SLOW LOGS; +SELECT * FROM t1 WHERE a=10; +a +10 +Warnings: +Note 1105 Cannot use key `a` part[0] for lookup: `test`.`t1`.`a` of type `varchar` = "10" of type `int` +EXPLAIN SELECT * FROM t1 WHERE a=10; +id select_type table type possible_keys key key_len ref rows Extra +1 SIMPLE t1 index a a 13 NULL 32 Using where; Using index +Warnings: +Note 1105 Cannot use key `a` part[0] for lookup: `test`.`t1`.`a` of type `varchar` = "10" of type `int` +NOT FOUND /# Warnings/ in log_slow_debug-3.log +NOT FOUND /# Note.*Cannot use key.*varchar.*10.*int/ in log_slow_debug-3.log +set @@global.slow_query_log_file= @org_slow_query_log_file; +DROP TABLE t1; +# +# MDEV-30820: slow log Rows_examined out of range +# +CREATE TABLE `tab_MDEV_30820` ( +`ID` int(11) NOT NULL AUTO_INCREMENT, +`A` int(11), +PRIMARY KEY(ID) +); +insert into tab_MDEV_30820 values (null, 0),(null, 0); +SET @old_slow_query_log= @@global.slow_query_log; +SET @old_log_output= @@global.log_output; +SET @old_long_query_time= @@long_query_time; +SET @old_dbug= @@GLOBAL.debug_dbug; +SET GLOBAL log_output= "TABLE"; +SET GLOBAL slow_query_log= ON; +SET SESSION long_query_time= 0; +SET GLOBAL debug_dbug="+d,debug_huge_number_of_examined_rows"; +SELECT * FROM tab_MDEV_30820 ORDER BY 1; +ID A +1 0 +2 0 +SET GLOBAL debug_dbug=@old_dbug; +SET @@long_query_time= @old_long_query_time; +SET @@global.log_output= @old_log_output; +SET @@global.slow_query_log= @old_slow_query_log; +drop table tab_MDEV_30820; +# +# End of 10.4 test +# +# # Clean up # SET SESSION debug_dbug=@saved_dbug; diff --git a/mysql-test/main/log_slow_debug.test b/mysql-test/main/log_slow_debug.test index aba4cbc8dcb..ee0406112d2 100644 --- a/mysql-test/main/log_slow_debug.test +++ b/mysql-test/main/log_slow_debug.test @@ -1,4 +1,5 @@ -- source include/have_debug.inc +-- source include/have_sequence.inc SET @org_slow_query_log= @@global.slow_query_log; SET @org_log_output= @@global.log_output; @@ -82,6 +83,108 @@ TRUNCATE TABLE mysql.slow_log; --source include/log_slow_debug_common.inc CALL show_slow_log(); +--echo # +--echo # Start of 10.6 tests +--echo # + +--echo # +--echo # MDEV-32203 Raise notes when an index cannot be used on data type +--echo # mismatch +--echo # + +CREATE TABLE t1 (a VARCHAR(10), KEY(a)); +insert into t1 select seq from seq_0_to_31; + +SET note_verbosity=all; +SET log_slow_verbosity=all; +SET global log_output='FILE'; +set @org_slow_query_log_file=@@global.slow_query_log_file; + +--replace_result $MYSQLTEST_VARDIR MYSQLTEST_VARDIR +eval set global slow_query_log_file='$MYSQLTEST_VARDIR/tmp/log_slow_debug-1.log'; +FLUSH SLOW LOGS; +--disable_ps_protocol +SELECT * FROM t1 WHERE a=10; +EXPLAIN SELECT * FROM t1 WHERE a=10; +--enable_ps_protocol + +--let SEARCH_FILE = `SELECT @@slow_query_log_file` +--let SEARCH_PATTERN=# Warnings +--source include/search_pattern_in_file.inc +--let SEARCH_PATTERN= # Note.*Cannot use key.*varchar.*10.*int +--source include/search_pattern_in_file.inc + +--replace_result $MYSQLTEST_VARDIR MYSQLTEST_VARDIR +eval set global slow_query_log_file='$MYSQLTEST_VARDIR/tmp/log_slow_debug-2.log'; +SET note_verbosity="explain"; +FLUSH SLOW LOGS; +EXPLAIN SELECT * FROM t1 WHERE a=10; + +--let SEARCH_FILE = `SELECT @@slow_query_log_file` +--let SEARCH_PATTERN=# Warnings +--source include/search_pattern_in_file.inc +--let SEARCH_PATTERN= # Note.*Cannot use key.*varchar.*10.*int +--source include/search_pattern_in_file.inc + +--replace_result $MYSQLTEST_VARDIR MYSQLTEST_VARDIR +eval set global slow_query_log_file='$MYSQLTEST_VARDIR/tmp/log_slow_debug-3.log'; +SET log_slow_verbosity=replace(@@log_slow_verbosity, "warnings", ""); +SET log_slow_verbosity=replace(@@log_slow_verbosity, "full", ""); +SET note_verbosity=all; +FLUSH SLOW LOGS; +SELECT * FROM t1 WHERE a=10; +EXPLAIN SELECT * FROM t1 WHERE a=10; + +--let SEARCH_FILE = `SELECT @@slow_query_log_file` +--let SEARCH_PATTERN=# Warnings +--source include/search_pattern_in_file.inc +--let SEARCH_PATTERN= # Note.*Cannot use key.*varchar.*10.*int +--source include/search_pattern_in_file.inc + +set @@global.slow_query_log_file= @org_slow_query_log_file; + +--remove_file $MYSQLTEST_VARDIR/tmp/log_slow_debug-1.log +--remove_file $MYSQLTEST_VARDIR/tmp/log_slow_debug-2.log +--remove_file $MYSQLTEST_VARDIR/tmp/log_slow_debug-3.log + +DROP TABLE t1; + +--echo # +--echo # MDEV-30820: slow log Rows_examined out of range +--echo # + +CREATE TABLE `tab_MDEV_30820` ( +`ID` int(11) NOT NULL AUTO_INCREMENT, +`A` int(11), +PRIMARY KEY(ID) +); + +insert into tab_MDEV_30820 values (null, 0),(null, 0); + +SET @old_slow_query_log= @@global.slow_query_log; +SET @old_log_output= @@global.log_output; +SET @old_long_query_time= @@long_query_time; +SET @old_dbug= @@GLOBAL.debug_dbug; +SET GLOBAL log_output= "TABLE"; + +SET GLOBAL slow_query_log= ON; +SET SESSION long_query_time= 0; + +SET GLOBAL debug_dbug="+d,debug_huge_number_of_examined_rows"; +SELECT * FROM tab_MDEV_30820 ORDER BY 1; +SET GLOBAL debug_dbug=@old_dbug; + + +## Reset to initial values +SET @@long_query_time= @old_long_query_time; +SET @@global.log_output= @old_log_output; +SET @@global.slow_query_log= @old_slow_query_log; + +drop table tab_MDEV_30820; + +--echo # +--echo # End of 10.4 test +--echo # --echo # --echo # Clean up diff --git a/mysql-test/main/log_tables.result b/mysql-test/main/log_tables.result index d4f1f59ec1c..1d642c0ade1 100644 --- a/mysql-test/main/log_tables.result +++ b/mysql-test/main/log_tables.result @@ -73,15 +73,15 @@ slow_log CREATE TABLE `slow_log` ( `user_host` mediumtext NOT NULL, `query_time` time(6) NOT NULL, `lock_time` time(6) NOT NULL, - `rows_sent` int(11) NOT NULL, - `rows_examined` int(11) NOT NULL, + `rows_sent` bigint(20) unsigned NOT NULL, + `rows_examined` bigint(20) unsigned NOT NULL, `db` varchar(512) NOT NULL, `last_insert_id` int(11) NOT NULL, `insert_id` int(11) NOT NULL, `server_id` int(10) unsigned NOT NULL, `sql_text` mediumtext NOT NULL, `thread_id` bigint(21) unsigned NOT NULL, - `rows_affected` int(11) NOT NULL + `rows_affected` bigint(20) unsigned NOT NULL ) ENGINE=CSV DEFAULT CHARSET=utf8mb3 COLLATE=utf8mb3_general_ci COMMENT='Slow log' show fields from mysql.slow_log; Field Type Null Key Default Extra @@ -89,15 +89,15 @@ start_time timestamp(6) NO current_timestamp(6) on update current_timestamp(6) user_host mediumtext NO NULL query_time time(6) NO NULL lock_time time(6) NO NULL -rows_sent int(11) NO NULL -rows_examined int(11) NO NULL +rows_sent bigint(20) unsigned NO NULL +rows_examined bigint(20) unsigned NO NULL db varchar(512) NO NULL last_insert_id int(11) NO NULL insert_id int(11) NO NULL server_id int(10) unsigned NO NULL sql_text mediumtext NO NULL thread_id bigint(21) unsigned NO NULL -rows_affected int(11) NO NULL +rows_affected bigint(20) unsigned NO NULL flush logs; flush tables; SET GLOBAL GENERAL_LOG=ON; @@ -180,15 +180,15 @@ slow_log CREATE TABLE `slow_log` ( `user_host` mediumtext NOT NULL, `query_time` time(6) NOT NULL, `lock_time` time(6) NOT NULL, - `rows_sent` int(11) NOT NULL, - `rows_examined` int(11) NOT NULL, + `rows_sent` bigint(20) unsigned NOT NULL, + `rows_examined` bigint(20) unsigned NOT NULL, `db` varchar(512) NOT NULL, `last_insert_id` int(11) NOT NULL, `insert_id` int(11) NOT NULL, `server_id` int(10) unsigned NOT NULL, `sql_text` mediumtext NOT NULL, `thread_id` bigint(21) unsigned NOT NULL, - `rows_affected` int(11) NOT NULL + `rows_affected` bigint(20) unsigned NOT NULL ) ENGINE=CSV DEFAULT CHARSET=utf8mb3 COLLATE=utf8mb3_general_ci COMMENT='Slow log' alter table mysql.general_log engine=myisam; alter table mysql.slow_log engine=myisam; @@ -209,15 +209,15 @@ slow_log CREATE TABLE `slow_log` ( `user_host` mediumtext NOT NULL, `query_time` time(6) NOT NULL, `lock_time` time(6) NOT NULL, - `rows_sent` int(11) NOT NULL, - `rows_examined` int(11) NOT NULL, + `rows_sent` bigint(20) unsigned NOT NULL, + `rows_examined` bigint(20) unsigned NOT NULL, `db` varchar(512) NOT NULL, `last_insert_id` int(11) NOT NULL, `insert_id` int(11) NOT NULL, `server_id` int(10) unsigned NOT NULL, `sql_text` mediumtext NOT NULL, `thread_id` bigint(21) unsigned NOT NULL, - `rows_affected` int(11) NOT NULL + `rows_affected` bigint(20) unsigned NOT NULL ) ENGINE=MyISAM DEFAULT CHARSET=utf8mb3 COLLATE=utf8mb3_general_ci COMMENT='Slow log' set global general_log='ON'; set global slow_query_log='ON'; @@ -287,15 +287,15 @@ ON UPDATE CURRENT_TIMESTAMP, `user_host` mediumtext NOT NULL, `query_time` time(6) NOT NULL, `lock_time` time(6) NOT NULL, -`rows_sent` int(11) NOT NULL, -`rows_examined` int(11) NOT NULL, +`rows_sent` bigint(20) unsigned NOT NULL, +`rows_examined` bigint(20) unsigned NOT NULL, `db` varchar(512) NOT NULL, `last_insert_id` int(11) NOT NULL, `insert_id` int(11) NOT NULL, `server_id` int(10) unsigned NOT NULL, `sql_text` mediumtext NOT NULL, `thread_id` BIGINT(21) UNSIGNED NOT NULL, -`rows_affected` int(11) NOT NULL +`rows_affected` bigint(20) unsigned NOT NULL ) ENGINE=CSV DEFAULT CHARSET=utf8 COMMENT='Slow log'; set global general_log='ON'; set global slow_query_log='ON'; @@ -580,15 +580,15 @@ CREATE TABLE `db_17876.slow_log_data` ( `user_host` mediumtext , `query_time` time(6) , `lock_time` time(6) , -`rows_sent` int(11) , -`rows_examined` int(11) , +`rows_sent` bigint(20) unsigned, +`rows_examined` bigint(20) unsigned, `db` varchar(512) default NULL, `last_insert_id` int(11) default NULL, `insert_id` int(11) default NULL, `server_id` int(11) default NULL, `sql_text` mediumtext, `thread_id` bigint(21) unsigned default NULL, -`rows_affected` int(11) default NULL +`rows_affected` bigint(20) unsigned default NULL ); CREATE TABLE `db_17876.general_log_data` ( `event_time` timestamp(6) NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP, diff --git a/mysql-test/main/log_tables.test b/mysql-test/main/log_tables.test index 3ce49a21e7d..1eee6be0524 100644 --- a/mysql-test/main/log_tables.test +++ b/mysql-test/main/log_tables.test @@ -307,15 +307,15 @@ CREATE TABLE `slow_log` ( `user_host` mediumtext NOT NULL, `query_time` time(6) NOT NULL, `lock_time` time(6) NOT NULL, - `rows_sent` int(11) NOT NULL, - `rows_examined` int(11) NOT NULL, + `rows_sent` bigint(20) unsigned NOT NULL, + `rows_examined` bigint(20) unsigned NOT NULL, `db` varchar(512) NOT NULL, `last_insert_id` int(11) NOT NULL, `insert_id` int(11) NOT NULL, `server_id` int(10) unsigned NOT NULL, `sql_text` mediumtext NOT NULL, `thread_id` BIGINT(21) UNSIGNED NOT NULL, - `rows_affected` int(11) NOT NULL + `rows_affected` bigint(20) unsigned NOT NULL ) ENGINE=CSV DEFAULT CHARSET=utf8 COMMENT='Slow log'; set global general_log='ON'; @@ -743,15 +743,15 @@ CREATE TABLE `db_17876.slow_log_data` ( `user_host` mediumtext , `query_time` time(6) , `lock_time` time(6) , - `rows_sent` int(11) , - `rows_examined` int(11) , + `rows_sent` bigint(20) unsigned, + `rows_examined` bigint(20) unsigned, `db` varchar(512) default NULL, `last_insert_id` int(11) default NULL, `insert_id` int(11) default NULL, `server_id` int(11) default NULL, `sql_text` mediumtext, `thread_id` bigint(21) unsigned default NULL, - `rows_affected` int(11) default NULL + `rows_affected` bigint(20) unsigned default NULL ); CREATE TABLE `db_17876.general_log_data` ( diff --git a/mysql-test/main/long_unique_bugs.result b/mysql-test/main/long_unique_bugs.result index ed13c668ec3..ce44ae2b6fb 100644 --- a/mysql-test/main/long_unique_bugs.result +++ b/mysql-test/main/long_unique_bugs.result @@ -457,6 +457,41 @@ create table t1 (f text not null, unique (f)); insert into t1 (f) select 'f'; drop table t1; # +# MDEV-32012 hash unique corrupts index on virtual blobs +# +create table t1 ( +f1 varchar(25), +v1 mediumtext generated always as (concat('f1:', f1)) virtual, +unique key (f1) using hash, +key (v1(1000)) +); +flush status; +insert ignore t1 (f1) values (9599),(94410); +show status like 'handler_read_next'; +Variable_name Value +Handler_read_next 1 +# the above MUST BE =1 +check table t1 extended; +Table Op Msg_type Msg_text +test.t1 check status OK +update t1 set f1=100 where f1=9599; +update t1 set f1=9599 where f1=100; +check table t1 extended; +Table Op Msg_type Msg_text +test.t1 check status OK +drop table t1; +# +# MDEV-32015 insert into an empty table fails with hash unique +# +create table t1 (f1 varchar(25), unique (f1) using hash); +insert ignore t1 (f1) values ('new york'),('virginia'),('spouse'),(null),('zqekmqpwutxnzddrbjycyo'),('nebraska'),('illinois'),('qe'),('ekmqpwut'),('arizona'),('arizona'); +Warnings: +Warning 1062 Duplicate entry 'arizona' for key 'f1' +check table t1 extended; +Table Op Msg_type Msg_text +test.t1 check status OK +drop table t1; +# # End of 10.4 tests # # diff --git a/mysql-test/main/long_unique_bugs.test b/mysql-test/main/long_unique_bugs.test index c7914d1e5dd..c06b4169afe 100644 --- a/mysql-test/main/long_unique_bugs.test +++ b/mysql-test/main/long_unique_bugs.test @@ -456,6 +456,38 @@ create table t1 (f text not null, unique (f)); insert into t1 (f) select 'f'; drop table t1; +--echo # +--echo # MDEV-32012 hash unique corrupts index on virtual blobs +--echo # +create table t1 ( + f1 varchar(25), + v1 mediumtext generated always as (concat('f1:', f1)) virtual, + unique key (f1) using hash, + key (v1(1000)) +); +flush status; +insert ignore t1 (f1) values (9599),(94410); +# handler_read_next must be 1 below, meaning there was a hash collision above. +# if a change in the hash function causes these values not to collide anymore, +# the test must be adjusted to use some other values that collide. +# to find a collision add an assert into check_duplicate_long_entry_key() +# and run, like, insert...select * seq_from_1_to_1000000000 +show status like 'handler_read_next'; +--echo # the above MUST BE =1 +check table t1 extended; +update t1 set f1=100 where f1=9599; +update t1 set f1=9599 where f1=100; +check table t1 extended; +drop table t1; + +--echo # +--echo # MDEV-32015 insert into an empty table fails with hash unique +--echo # +create table t1 (f1 varchar(25), unique (f1) using hash); +insert ignore t1 (f1) values ('new york'),('virginia'),('spouse'),(null),('zqekmqpwutxnzddrbjycyo'),('nebraska'),('illinois'),('qe'),('ekmqpwut'),('arizona'),('arizona'); +check table t1 extended; +drop table t1; + --echo # --echo # End of 10.4 tests --echo # diff --git a/mysql-test/main/long_unique_bugs_replication.result b/mysql-test/main/long_unique_bugs_replication.result index af583d00cea..39b0ebe26d2 100644 --- a/mysql-test/main/long_unique_bugs_replication.result +++ b/mysql-test/main/long_unique_bugs_replication.result @@ -1,3 +1,6 @@ +# +# MDEV-22722 Assertion "inited==NONE" failed in handler::ha_index_init on the slave during UPDATE +# include/master-slave.inc [connection master] create table t1 (i1 int, a1 text, unique key i1 (a1)) engine=myisam; @@ -6,7 +9,21 @@ insert into t1 values (2,2); update t1 set a1 = 'd' limit 1; update t1 set a1 = 'd2' where i1= 2; connection slave; -connection slave; connection master; drop table t1; +# +# MDEV-32093 long uniques break old->new replication +# +connection slave; +create table t1 (id int not null, b1 varchar(255) not null, b2 varchar(2550) not null, unique (id), unique key (b1,b2) using hash) default charset utf8mb3; +set global slave_exec_mode=idempotent; +binlog 'aRf2ZA8BAAAA/AAAAAABAAAAAAQAMTAuNS4xNS1NYXJpYURCLWxvZwAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAABpF/ZkEzgNAAgAEgAEBAQEEgAA5AAEGggAAAAICAgCAAAACgoKAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAEEwQADQgICAoKCgFRmTlk'; +binlog 'bBf2ZBMBAAAANAAAAJgHAAAAAHEAAAAAAAEABHRlc3QAAnQxAAQDDw8IBP0C4h0AeqMD4A==bBf2ZBcBAAAANAAAAMwHAAAAAHEAAAAAAAEABP/wj6QAAAEAYgEAZa6/VU0JAAAANteqUw=='; +binlog 'bBf2ZBMBAAAANAAAAJgHAAAAAHEAAAAAAAEABHRlc3QAAnQxAAQDDw8IBP0C4h0AeqMD4A==bBf2ZBcBAAAANAAAAMwHAAAAAHEAAAAAAAEABP/wj6QAAAEAYgEAZa6/VU0JAAAANteqUw=='; +binlog 'bBf2ZBMBAAAANAAAAHUkAAAAAHEAAAAAAAEABHRlc3QAAnQxAAQDDw8IBP0C4h0AaTGFIg==bBf2ZBgBAAAASAAAAL0kAAAAAHEAAAAAAAEABP//8I+kAAABAGIBAGWuv1VNCQAAAPBuWwAAAQBiAQBlrr9VTQkAAADxS9Lu'; +drop table t1; +set global slave_exec_mode=default; +# +# End of 10.4 tests +# include/rpl_end.inc diff --git a/mysql-test/main/long_unique_bugs_replication.test b/mysql-test/main/long_unique_bugs_replication.test index 1cacd088bee..9c44d13e6a5 100644 --- a/mysql-test/main/long_unique_bugs_replication.test +++ b/mysql-test/main/long_unique_bugs_replication.test @@ -2,9 +2,9 @@ # Long unique bugs related to master slave replication # -# -# MDEV-22722 Assertion "inited==NONE" failed in handler::ha_index_init on the slave during UPDATE -# +--echo # +--echo # MDEV-22722 Assertion "inited==NONE" failed in handler::ha_index_init on the slave during UPDATE +--echo # --source include/have_binlog_format_row.inc --source include/master-slave.inc @@ -16,9 +16,34 @@ update t1 set a1 = 'd' limit 1; update t1 set a1 = 'd2' where i1= 2; sync_slave_with_master; -connection slave; connection master; drop table t1; +--echo # +--echo # MDEV-32093 long uniques break old->new replication +--echo # + +# this is techically a bug in replication, but it needs an old master +# so we'll run it as a non-replicated test with BINLOG command +sync_slave_with_master; +create table t1 (id int not null, b1 varchar(255) not null, b2 varchar(2550) not null, unique (id), unique key (b1,b2) using hash) default charset utf8mb3; +set global slave_exec_mode=idempotent; + +# Format_description_log_event, MariaDB-10.5.15 +binlog 'aRf2ZA8BAAAA/AAAAAABAAAAAAQAMTAuNS4xNS1NYXJpYURCLWxvZwAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAABpF/ZkEzgNAAgAEgAEBAQEEgAA5AAEGggAAAAICAgCAAAACgoKAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAEEwQADQgICAoKCgFRmTlk'; + +### INSERT t1 VALUES (42127, 'b', 'e', 39952170926) +binlog 'bBf2ZBMBAAAANAAAAJgHAAAAAHEAAAAAAAEABHRlc3QAAnQxAAQDDw8IBP0C4h0AeqMD4A==bBf2ZBcBAAAANAAAAMwHAAAAAHEAAAAAAAEABP/wj6QAAAEAYgEAZa6/VU0JAAAANteqUw=='; +binlog 'bBf2ZBMBAAAANAAAAJgHAAAAAHEAAAAAAAEABHRlc3QAAnQxAAQDDw8IBP0C4h0AeqMD4A==bBf2ZBcBAAAANAAAAMwHAAAAAHEAAAAAAAEABP/wj6QAAAEAYgEAZa6/VU0JAAAANteqUw=='; + +### UPDATE t1 WHERE (42127, 'b', 'e', 39952170926) SET (23406, 'b', 'e', 39952170926) +binlog 'bBf2ZBMBAAAANAAAAHUkAAAAAHEAAAAAAAEABHRlc3QAAnQxAAQDDw8IBP0C4h0AaTGFIg==bBf2ZBgBAAAASAAAAL0kAAAAAHEAAAAAAAEABP//8I+kAAABAGIBAGWuv1VNCQAAAPBuWwAAAQBiAQBlrr9VTQkAAADxS9Lu'; + +drop table t1; +set global slave_exec_mode=default; + +--echo # +--echo # End of 10.4 tests +--echo # --source include/rpl_end.inc diff --git a/mysql-test/main/lowercase_table_grant.result b/mysql-test/main/lowercase_table_grant.result index 45b6ab0410f..0d84eb15ee8 100644 --- a/mysql-test/main/lowercase_table_grant.result +++ b/mysql-test/main/lowercase_table_grant.result @@ -7,8 +7,8 @@ Grants for mysqltest_1@localhost GRANT USAGE ON *.* TO `mysqltest_1`@`localhost` GRANT ALL PRIVILEGES ON `mysqltest`.* TO `mysqltest_1`@`localhost` select * from db where user = 'mysqltest_1'; -Host Db User Select_priv Insert_priv Update_priv Delete_priv Create_priv Drop_priv Grant_priv References_priv Index_priv Alter_priv Create_tmp_table_priv Lock_tables_priv Create_view_priv Show_view_priv Create_routine_priv Alter_routine_priv Execute_priv Event_priv Trigger_priv Delete_history_priv -localhost mysqltest mysqltest_1 Y Y Y Y Y Y N Y Y Y Y Y Y Y Y Y Y Y Y Y +Host Db User Select_priv Insert_priv Update_priv Delete_priv Create_priv Drop_priv Grant_priv References_priv Index_priv Alter_priv Create_tmp_table_priv Lock_tables_priv Create_view_priv Show_view_priv Create_routine_priv Alter_routine_priv Execute_priv Event_priv Trigger_priv Delete_history_priv Show_create_routine_priv +localhost mysqltest mysqltest_1 Y Y Y Y Y Y N Y Y Y Y Y Y Y Y Y Y Y Y Y Y update db set db = 'MYSQLtest' where db = 'mysqltest' and user = 'mysqltest_1' and host = 'localhost'; flush privileges; show grants for mysqltest_1@localhost; @@ -16,8 +16,8 @@ Grants for mysqltest_1@localhost GRANT USAGE ON *.* TO `mysqltest_1`@`localhost` GRANT ALL PRIVILEGES ON `mysqltest`.* TO `mysqltest_1`@`localhost` select * from db where user = 'mysqltest_1'; -Host Db User Select_priv Insert_priv Update_priv Delete_priv Create_priv Drop_priv Grant_priv References_priv Index_priv Alter_priv Create_tmp_table_priv Lock_tables_priv Create_view_priv Show_view_priv Create_routine_priv Alter_routine_priv Execute_priv Event_priv Trigger_priv Delete_history_priv -localhost MYSQLtest mysqltest_1 Y Y Y Y Y Y N Y Y Y Y Y Y Y Y Y Y Y Y Y +Host Db User Select_priv Insert_priv Update_priv Delete_priv Create_priv Drop_priv Grant_priv References_priv Index_priv Alter_priv Create_tmp_table_priv Lock_tables_priv Create_view_priv Show_view_priv Create_routine_priv Alter_routine_priv Execute_priv Event_priv Trigger_priv Delete_history_priv Show_create_routine_priv +localhost MYSQLtest mysqltest_1 Y Y Y Y Y Y N Y Y Y Y Y Y Y Y Y Y Y Y Y Y delete from db where db = 'MYSQLtest' and user = 'mysqltest_1' and host = 'localhost'; flush privileges; drop user mysqltest_1@localhost; diff --git a/mysql-test/main/mrr_icp_extra.result b/mysql-test/main/mrr_icp_extra.result index 8f6ee88acc6..1b33b008f35 100644 --- a/mysql-test/main/mrr_icp_extra.result +++ b/mysql-test/main/mrr_icp_extra.result @@ -30,6 +30,8 @@ id select_type table type possible_keys key key_len ref rows Extra EXPLAIN SELECT * FROM t1 WHERE s2='a' COLLATE latin1_german1_ci; id select_type table type possible_keys key key_len ref rows Extra 1 SIMPLE t1 ALL s2 NULL NULL NULL 10 Using where +Warnings: +Note 1105 Cannot use key `s2` part[0] for lookup: `test`.`t1`.`s2` of collation `latin1_swedish_ci` = "'a' collate latin1_german1_ci" of collation `latin1_german1_ci` EXPLAIN SELECT * FROM t1 WHERE s1 BETWEEN 'a' AND 'b' COLLATE latin1_german1_ci; id select_type table type possible_keys key key_len ref rows Extra 1 SIMPLE t1 range s1 s1 11 NULL 2 Using index condition; Rowid-ordered scan diff --git a/mysql-test/main/myisam_explain_non_select_all.result b/mysql-test/main/myisam_explain_non_select_all.result index eaeb371d535..b036d4870cd 100644 --- a/mysql-test/main/myisam_explain_non_select_all.result +++ b/mysql-test/main/myisam_explain_non_select_all.result @@ -1384,12 +1384,17 @@ INSERT INTO t1 (i) VALUES (10),(11),(12),(13),(14),(15),(16),(17),(18),(19), EXPLAIN DELETE FROM t1 WHERE i > 10 AND i <= 18 ORDER BY i LIMIT 5; id select_type table type possible_keys key key_len ref rows Extra 1 SIMPLE t1 ALL NULL NULL NULL NULL 26 Using where; Using filesort +Warnings: +Note 1105 Cannot use key `i` part[0] for lookup: `test`.`t1`.`i` of type `char` >= "10" of type `int` +Note 1105 Cannot use key `i` part[0] for lookup: `test`.`t1`.`i` of type `char` <= "18" of type `int` FLUSH STATUS; FLUSH TABLES; EXPLAIN EXTENDED DELETE FROM t1 WHERE i > 10 AND i <= 18 ORDER BY i LIMIT 5; id select_type table type possible_keys key key_len ref rows filtered Extra 1 SIMPLE t1 ALL NULL NULL NULL NULL 26 100.00 Using where; Using filesort Warnings: +Note 1105 Cannot use key `i` part[0] for lookup: `test`.`t1`.`i` of type `char` >= "10" of type `int` +Note 1105 Cannot use key `i` part[0] for lookup: `test`.`t1`.`i` of type `char` <= "18" of type `int` Note 1003 delete from `test`.`t1` using dual where `test`.`t1`.`i` > 10 and `test`.`t1`.`i` <= 18 order by `test`.`t1`.`i` limit 5 # Status of EXPLAIN EXTENDED query Variable_name Value @@ -1400,6 +1405,8 @@ EXPLAIN EXTENDED SELECT * FROM t1 WHERE i > 10 AND i <= 18 ORDER BY i LIMIT 5; id select_type table type possible_keys key key_len ref rows filtered Extra 1 SIMPLE t1 ALL i NULL NULL NULL 26 100.00 Using where; Using filesort Warnings: +Note 1105 Cannot use key `i` part[0] for lookup: `test`.`t1`.`i` of type `char` >= "10" of type `int` +Note 1105 Cannot use key `i` part[0] for lookup: `test`.`t1`.`i` of type `char` <= "18" of type `int` Note 1003 select `test`.`t1`.`a` AS `a`,`test`.`t1`.`i` AS `i` from `test`.`t1` where `test`.`t1`.`i` > 10 and `test`.`t1`.`i` <= 18 order by `test`.`t1`.`i` limit 5 # Status of EXPLAIN EXTENDED "equivalent" SELECT query execution Variable_name Value @@ -1530,12 +1537,15 @@ INSERT INTO t2 SELECT i, i, i, i FROM t1; EXPLAIN DELETE FROM t2 WHERE b = 10 ORDER BY a, c LIMIT 5; id select_type table type possible_keys key key_len ref rows Extra 1 SIMPLE t2 ALL NULL NULL NULL NULL 26 Using where; Using filesort +Warnings: +Note 1105 Cannot use key `a` part[1] for lookup: `test`.`t2`.`b` of type `char` = "10" of type `int` FLUSH STATUS; FLUSH TABLES; EXPLAIN EXTENDED DELETE FROM t2 WHERE b = 10 ORDER BY a, c LIMIT 5; id select_type table type possible_keys key key_len ref rows filtered Extra 1 SIMPLE t2 ALL NULL NULL NULL NULL 26 100.00 Using where; Using filesort Warnings: +Note 1105 Cannot use key `a` part[1] for lookup: `test`.`t2`.`b` of type `char` = "10" of type `int` Note 1003 delete from `test`.`t2` using dual where `test`.`t2`.`b` = 10 order by `test`.`t2`.`a`,`test`.`t2`.`c` limit 5 # Status of EXPLAIN EXTENDED query Variable_name Value @@ -1546,6 +1556,7 @@ EXPLAIN EXTENDED SELECT * FROM t2 WHERE b = 10 ORDER BY a, c LIMIT 5; id select_type table type possible_keys key key_len ref rows filtered Extra 1 SIMPLE t2 ALL NULL NULL NULL NULL 26 100.00 Using where; Using filesort Warnings: +Note 1105 Cannot use key `a` part[1] for lookup: `test`.`t2`.`b` of type `char` = "10" of type `int` Note 1003 select `test`.`t2`.`a` AS `a`,`test`.`t2`.`b` AS `b`,`test`.`t2`.`c` AS `c`,`test`.`t2`.`d` AS `d` from `test`.`t2` where `test`.`t2`.`b` = 10 order by `test`.`t2`.`a`,`test`.`t2`.`c` limit 5 # Status of EXPLAIN EXTENDED "equivalent" SELECT query execution Variable_name Value @@ -1582,12 +1593,15 @@ INSERT INTO t2 SELECT i, i, i, i FROM t1; EXPLAIN DELETE FROM t2 WHERE b = 10 ORDER BY a, c LIMIT 5; id select_type table type possible_keys key key_len ref rows Extra 1 SIMPLE t2 ALL NULL NULL NULL NULL 26 Using where; Using filesort +Warnings: +Note 1105 Cannot use key `a` part[1] for lookup: `test`.`t2`.`b` of type `char` = "10" of type `int` FLUSH STATUS; FLUSH TABLES; EXPLAIN EXTENDED DELETE FROM t2 WHERE b = 10 ORDER BY a, c LIMIT 5; id select_type table type possible_keys key key_len ref rows filtered Extra 1 SIMPLE t2 ALL NULL NULL NULL NULL 26 100.00 Using where; Using filesort Warnings: +Note 1105 Cannot use key `a` part[1] for lookup: `test`.`t2`.`b` of type `char` = "10" of type `int` Note 1003 delete from `test`.`t2` using dual where `test`.`t2`.`b` = 10 order by `test`.`t2`.`a`,`test`.`t2`.`c` limit 5 # Status of EXPLAIN EXTENDED query Variable_name Value @@ -1598,6 +1612,7 @@ EXPLAIN EXTENDED SELECT * FROM t2 WHERE b = 10 ORDER BY a, c LIMIT 5; id select_type table type possible_keys key key_len ref rows filtered Extra 1 SIMPLE t2 ALL NULL NULL NULL NULL 26 100.00 Using where; Using filesort Warnings: +Note 1105 Cannot use key `a` part[1] for lookup: `test`.`t2`.`b` of type `char` = "10" of type `int` Note 1003 select `test`.`t2`.`a` AS `a`,`test`.`t2`.`b` AS `b`,`test`.`t2`.`c` AS `c`,`test`.`t2`.`d` AS `d` from `test`.`t2` where `test`.`t2`.`b` = 10 order by `test`.`t2`.`a`,`test`.`t2`.`c` limit 5 # Status of EXPLAIN EXTENDED "equivalent" SELECT query execution Variable_name Value @@ -1876,12 +1891,17 @@ INSERT INTO t2 (i) SELECT i FROM t1; EXPLAIN UPDATE t2 SET a = 10 WHERE i > 10 AND i <= 18 ORDER BY i LIMIT 5; id select_type table type possible_keys key key_len ref rows Extra 1 SIMPLE t2 ALL NULL NULL NULL NULL 26 Using where; Using filesort +Warnings: +Note 1105 Cannot use key `i` part[0] for lookup: `test`.`t2`.`i` of type `char` >= "10" of type `int` +Note 1105 Cannot use key `i` part[0] for lookup: `test`.`t2`.`i` of type `char` <= "18" of type `int` FLUSH STATUS; FLUSH TABLES; EXPLAIN EXTENDED UPDATE t2 SET a = 10 WHERE i > 10 AND i <= 18 ORDER BY i LIMIT 5; id select_type table type possible_keys key key_len ref rows filtered Extra 1 SIMPLE t2 ALL NULL NULL NULL NULL 26 100.00 Using where; Using filesort Warnings: +Note 1105 Cannot use key `i` part[0] for lookup: `test`.`t2`.`i` of type `char` >= "10" of type `int` +Note 1105 Cannot use key `i` part[0] for lookup: `test`.`t2`.`i` of type `char` <= "18" of type `int` Note 1003 update `test`.`t2` set `test`.`t2`.`a` = 10 where `test`.`t2`.`i` > 10 and `test`.`t2`.`i` <= 18 order by `test`.`t2`.`i` limit 5 # Status of EXPLAIN EXTENDED query Variable_name Value @@ -1892,6 +1912,8 @@ EXPLAIN EXTENDED SELECT * FROM t2 WHERE i > 10 AND i <= 18 ORDER BY i LIMIT id select_type table type possible_keys key key_len ref rows filtered Extra 1 SIMPLE t2 ALL i NULL NULL NULL 26 100.00 Using where; Using filesort Warnings: +Note 1105 Cannot use key `i` part[0] for lookup: `test`.`t2`.`i` of type `char` >= "10" of type `int` +Note 1105 Cannot use key `i` part[0] for lookup: `test`.`t2`.`i` of type `char` <= "18" of type `int` Note 1003 select `test`.`t2`.`a` AS `a`,`test`.`t2`.`i` AS `i` from `test`.`t2` where `test`.`t2`.`i` > 10 and `test`.`t2`.`i` <= 18 order by `test`.`t2`.`i` limit 5 # Status of EXPLAIN EXTENDED "equivalent" SELECT query execution Variable_name Value @@ -2025,12 +2047,15 @@ INSERT INTO t2 SELECT i, i, i, i FROM t1; EXPLAIN UPDATE t2 SET d = 10 WHERE b = 10 ORDER BY a, c LIMIT 5; id select_type table type possible_keys key key_len ref rows Extra 1 SIMPLE t2 ALL NULL NULL NULL NULL 26 Using where; Using filesort +Warnings: +Note 1105 Cannot use key `a` part[1] for lookup: `test`.`t2`.`b` of type `char` = "10" of type `int` FLUSH STATUS; FLUSH TABLES; EXPLAIN EXTENDED UPDATE t2 SET d = 10 WHERE b = 10 ORDER BY a, c LIMIT 5; id select_type table type possible_keys key key_len ref rows filtered Extra 1 SIMPLE t2 ALL NULL NULL NULL NULL 26 100.00 Using where; Using filesort Warnings: +Note 1105 Cannot use key `a` part[1] for lookup: `test`.`t2`.`b` of type `char` = "10" of type `int` Note 1003 update `test`.`t2` set `test`.`t2`.`d` = 10 where `test`.`t2`.`b` = 10 order by `test`.`t2`.`a`,`test`.`t2`.`c` limit 5 # Status of EXPLAIN EXTENDED query Variable_name Value @@ -2041,6 +2066,7 @@ EXPLAIN EXTENDED SELECT * FROM t2 WHERE b = 10 ORDER BY a, c LIMIT 5; id select_type table type possible_keys key key_len ref rows filtered Extra 1 SIMPLE t2 ALL NULL NULL NULL NULL 26 100.00 Using where; Using filesort Warnings: +Note 1105 Cannot use key `a` part[1] for lookup: `test`.`t2`.`b` of type `char` = "10" of type `int` Note 1003 select `test`.`t2`.`a` AS `a`,`test`.`t2`.`b` AS `b`,`test`.`t2`.`c` AS `c`,`test`.`t2`.`d` AS `d` from `test`.`t2` where `test`.`t2`.`b` = 10 order by `test`.`t2`.`a`,`test`.`t2`.`c` limit 5 # Status of EXPLAIN EXTENDED "equivalent" SELECT query execution Variable_name Value @@ -2077,12 +2103,15 @@ INSERT INTO t2 SELECT i, i, i, i FROM t1; EXPLAIN UPDATE t2 SET d = 10 WHERE b = 10 ORDER BY a, c LIMIT 5; id select_type table type possible_keys key key_len ref rows Extra 1 SIMPLE t2 ALL NULL NULL NULL NULL 26 Using where; Using filesort +Warnings: +Note 1105 Cannot use key `a` part[1] for lookup: `test`.`t2`.`b` of type `char` = "10" of type `int` FLUSH STATUS; FLUSH TABLES; EXPLAIN EXTENDED UPDATE t2 SET d = 10 WHERE b = 10 ORDER BY a, c LIMIT 5; id select_type table type possible_keys key key_len ref rows filtered Extra 1 SIMPLE t2 ALL NULL NULL NULL NULL 26 100.00 Using where; Using filesort Warnings: +Note 1105 Cannot use key `a` part[1] for lookup: `test`.`t2`.`b` of type `char` = "10" of type `int` Note 1003 update `test`.`t2` set `test`.`t2`.`d` = 10 where `test`.`t2`.`b` = 10 order by `test`.`t2`.`a`,`test`.`t2`.`c` limit 5 # Status of EXPLAIN EXTENDED query Variable_name Value @@ -2093,6 +2122,7 @@ EXPLAIN EXTENDED SELECT * FROM t2 WHERE b = 10 ORDER BY a, c LIMIT 5; id select_type table type possible_keys key key_len ref rows filtered Extra 1 SIMPLE t2 ALL NULL NULL NULL NULL 26 100.00 Using where; Using filesort Warnings: +Note 1105 Cannot use key `a` part[1] for lookup: `test`.`t2`.`b` of type `char` = "10" of type `int` Note 1003 select `test`.`t2`.`a` AS `a`,`test`.`t2`.`b` AS `b`,`test`.`t2`.`c` AS `c`,`test`.`t2`.`d` AS `d` from `test`.`t2` where `test`.`t2`.`b` = 10 order by `test`.`t2`.`a`,`test`.`t2`.`c` limit 5 # Status of EXPLAIN EXTENDED "equivalent" SELECT query execution Variable_name Value diff --git a/mysql-test/main/mysql_install_db_win.test b/mysql-test/main/mysql_install_db_win.test index fd3bf6d24b0..f6113847b8d 100644 --- a/mysql-test/main/mysql_install_db_win.test +++ b/mysql-test/main/mysql_install_db_win.test @@ -46,7 +46,7 @@ rmdir $ddir; # MDEV-28471 - mysql_install_db.exe fails with --innodb-page-size=64K --disable_result_log -exec $MYSQL_INSTALL_DB_EXE --datadir=$ddir --password=foo -R --innodb-page-size=64K --verbose +exec $MYSQL_INSTALL_DB_EXE --datadir=$ddir --password=foo -R --innodb-page-size=64K --verbose; --enable_result_log rmdir $ddir; diff --git a/mysql-test/main/mysql_upgrade.result b/mysql-test/main/mysql_upgrade.result index fe08d4135de..80fcb35865d 100644 --- a/mysql-test/main/mysql_upgrade.result +++ b/mysql-test/main/mysql_upgrade.result @@ -1895,7 +1895,7 @@ SET DEFAULT ROLE aRole; SHOW GRANTS; Grants for root@localhost GRANT `aRole` TO `root`@`localhost` WITH ADMIN OPTION -GRANT ALL PRIVILEGES ON *.* TO `root`@`localhost` WITH GRANT OPTION +GRANT SELECT, INSERT, UPDATE, DELETE, CREATE, DROP, RELOAD, SHUTDOWN, PROCESS, FILE, REFERENCES, INDEX, ALTER, SHOW DATABASES, SUPER, CREATE TEMPORARY TABLES, LOCK TABLES, EXECUTE, REPLICATION SLAVE, BINLOG MONITOR, CREATE VIEW, SHOW VIEW, CREATE ROUTINE, ALTER ROUTINE, CREATE USER, EVENT, TRIGGER, CREATE TABLESPACE, DELETE HISTORY, SET USER, FEDERATED ADMIN, CONNECTION ADMIN, READ_ONLY ADMIN, REPLICATION SLAVE ADMIN, REPLICATION MASTER ADMIN, BINLOG ADMIN, BINLOG REPLAY, SLAVE MONITOR ON *.* TO `root`@`localhost` WITH GRANT OPTION GRANT PROXY ON ''@'%' TO 'root'@'localhost' WITH GRANT OPTION GRANT USAGE ON *.* TO `aRole` SET DEFAULT ROLE `aRole` FOR `root`@`localhost` @@ -1903,7 +1903,7 @@ SET DEFAULT ROLE NONE; SHOW GRANTS; Grants for root@localhost GRANT `aRole` TO `root`@`localhost` WITH ADMIN OPTION -GRANT ALL PRIVILEGES ON *.* TO `root`@`localhost` WITH GRANT OPTION +GRANT SELECT, INSERT, UPDATE, DELETE, CREATE, DROP, RELOAD, SHUTDOWN, PROCESS, FILE, REFERENCES, INDEX, ALTER, SHOW DATABASES, SUPER, CREATE TEMPORARY TABLES, LOCK TABLES, EXECUTE, REPLICATION SLAVE, BINLOG MONITOR, CREATE VIEW, SHOW VIEW, CREATE ROUTINE, ALTER ROUTINE, CREATE USER, EVENT, TRIGGER, CREATE TABLESPACE, DELETE HISTORY, SET USER, FEDERATED ADMIN, CONNECTION ADMIN, READ_ONLY ADMIN, REPLICATION SLAVE ADMIN, REPLICATION MASTER ADMIN, BINLOG ADMIN, BINLOG REPLAY, SLAVE MONITOR ON *.* TO `root`@`localhost` WITH GRANT OPTION GRANT PROXY ON ''@'%' TO 'root'@'localhost' WITH GRANT OPTION GRANT USAGE ON *.* TO `aRole` DROP ROLE `aRole`; diff --git a/mysql-test/main/mysql_upgrade_to_100502.result b/mysql-test/main/mysql_upgrade_to_100502.result index 54f4d273c5e..8634b9b632a 100644 --- a/mysql-test/main/mysql_upgrade_to_100502.result +++ b/mysql-test/main/mysql_upgrade_to_100502.result @@ -8,7 +8,7 @@ CREATE USER user_all@localhost; GRANT ALL PRIVILEGES ON *.* TO user_all@localhost WITH GRANT OPTION; SHOW GRANTS FOR user_all@localhost; Grants for user_all@localhost -GRANT ALL PRIVILEGES ON *.* TO `user_all`@`localhost` WITH GRANT OPTION +GRANT SELECT, INSERT, UPDATE, DELETE, CREATE, DROP, RELOAD, SHUTDOWN, PROCESS, FILE, REFERENCES, INDEX, ALTER, SHOW DATABASES, SUPER, CREATE TEMPORARY TABLES, LOCK TABLES, EXECUTE, REPLICATION SLAVE, BINLOG MONITOR, CREATE VIEW, SHOW VIEW, CREATE ROUTINE, ALTER ROUTINE, CREATE USER, EVENT, TRIGGER, CREATE TABLESPACE, DELETE HISTORY, SET USER, FEDERATED ADMIN, CONNECTION ADMIN, READ_ONLY ADMIN, REPLICATION SLAVE ADMIN, REPLICATION MASTER ADMIN, BINLOG ADMIN, BINLOG REPLAY, SLAVE MONITOR ON *.* TO `user_all`@`localhost` WITH GRANT OPTION CREATE USER user_super@localhost; GRANT SUPER ON *.* TO user_super@localhost; SHOW GRANTS FOR user_super@localhost; @@ -56,7 +56,7 @@ FLUSH PRIVILEGES; # SHOW GRANTS FOR user_all@localhost; Grants for user_all@localhost -GRANT ALL PRIVILEGES ON *.* TO `user_all`@`localhost` WITH GRANT OPTION +GRANT SELECT, INSERT, UPDATE, DELETE, CREATE, DROP, RELOAD, SHUTDOWN, PROCESS, FILE, REFERENCES, INDEX, ALTER, SHOW DATABASES, SUPER, CREATE TEMPORARY TABLES, LOCK TABLES, EXECUTE, REPLICATION SLAVE, BINLOG MONITOR, CREATE VIEW, SHOW VIEW, CREATE ROUTINE, ALTER ROUTINE, CREATE USER, EVENT, TRIGGER, CREATE TABLESPACE, DELETE HISTORY, SET USER, FEDERATED ADMIN, CONNECTION ADMIN, READ_ONLY ADMIN, REPLICATION SLAVE ADMIN, REPLICATION MASTER ADMIN, BINLOG ADMIN, BINLOG REPLAY, SLAVE MONITOR ON *.* TO `user_all`@`localhost` WITH GRANT OPTION # # Should automatically get all new 10.5.2 priveleges that were splitted from SUPER # diff --git a/mysql-test/main/mysqlbinlog_row_compressed.test b/mysql-test/main/mysqlbinlog_row_compressed.test index 5c4aff00663..be9736347c9 100644 --- a/mysql-test/main/mysqlbinlog_row_compressed.test +++ b/mysql-test/main/mysqlbinlog_row_compressed.test @@ -4,6 +4,7 @@ --source include/have_log_bin.inc --source include/have_binlog_format_row.inc +--source include/have_normal_bzip.inc # # diff --git a/mysql-test/main/mysqlbinlog_stmt_compressed.test b/mysql-test/main/mysqlbinlog_stmt_compressed.test index 75dae6fa84e..08db2009d60 100644 --- a/mysql-test/main/mysqlbinlog_stmt_compressed.test +++ b/mysql-test/main/mysqlbinlog_stmt_compressed.test @@ -4,7 +4,7 @@ --source include/have_log_bin.inc --source include/have_binlog_format_statement.inc - +--source include/have_normal_bzip.inc # # # mysqlbinlog: compressed query event diff --git a/mysql-test/main/mysqld--help.result b/mysql-test/main/mysqld--help.result index 01ff752b8f2..d3a0a1f58fa 100644 --- a/mysql-test/main/mysqld--help.result +++ b/mysql-test/main/mysqld--help.result @@ -225,6 +225,7 @@ The following specify which files/extra groups are read (specified before remain Default flags for the regex library. Any combination of: DOTALL, DUPNAMES, EXTENDED, EXTENDED_MORE, EXTRA, MULTILINE, UNGREEDY + Use 'ALL' to set all combinations. --default-storage-engine=name The default storage engine for new tables --default-time-zone=name @@ -500,12 +501,14 @@ The following specify which files/extra groups are read (specified before remain --log-disabled-statements=name Don't log certain types of statements to general log. Any combination of: slave, sp + Use 'ALL' to set all combinations. --log-error[=name] Log errors to file (instead of stdout). If file name is not specified then 'datadir'/'log-basename'.err or the 'pid-file' path with extension .err is used --log-isam[=name] Log all MyISAM changes to file. --log-output=name How logs should be written. Any combination of: NONE, FILE, TABLE + Use 'ALL' to set all combinations. --log-queries-not-using-indexes Log queries that are executed without benefit of any index to the slow log if it is open. Same as @@ -524,15 +527,20 @@ The following specify which files/extra groups are read (specified before remain --log-slow-disabled-statements=name Don't log certain types of statements to slow log. Any combination of: admin, call, slave, sp + Use 'ALL' to set all combinations. --log-slow-filter=name Log only certain types of queries to the slow log. If - variable empty alll kind of queries are logged. All - types are bound by slow_query_time, except - 'not_using_index' which is always logged if enabled. Any - combination of: admin, filesort, filesort_on_disk, + variable empty all kind of queries are logged. All types + are bound by slow_query_time, except 'not_using_index' + which is always logged if enabled. Any combination of: + admin, filesort, filesort_on_disk, filesort_priority_queue, full_join, full_scan, not_using_index, query_cache, query_cache_miss, tmp_table, tmp_table_on_disk + Use 'ALL' to set all combinations. + --log-slow-max-warnings=# + Max numbers of warnings printed to slow query log per + statement --log-slow-min-examined-row-limit=# Don't write queries to slow log that examine fewer rows than that @@ -560,7 +568,8 @@ The following specify which files/extra groups are read (specified before remain (Defaults to on; use --skip-log-slow-slave-statements to disable.) --log-slow-verbosity=name Verbosity level for the slow log. Any combination of: - innodb, query_plan, explain, engine, full + innodb, query_plan, explain, engine, warnings, full + Use 'ALL' to set all combinations. --log-tc=name Path to transaction coordinator log (used for transactions that affect more than one storage engine, when binary log is disabled). @@ -677,6 +686,7 @@ The following specify which files/extra groups are read (specified before remain Specifies how corrupted tables should be automatically repaired. Any combination of: DEFAULT, BACKUP, FORCE, QUICK, BACKUP_ALL, OFF + Use 'ALL' to set all combinations. --myisam-repair-threads=# If larger than 1, when repairing a MyISAM table all indexes will be created in parallel, with one thread per @@ -705,6 +715,11 @@ The following specify which files/extra groups are read (specified before remain --net-write-timeout=# Number of seconds to wait for a block to be written to a connection before aborting the write + --note-verbosity=name + Verbosity level for note-warnings given to the user. See + also @@sql_notes.. Any combination of: basic, + unusable_keys, explain + Use 'ALL' to set all combinations. --old Use compatible behavior from previous MariaDB version. See also --old-mode --old-mode=name Used to emulate old behavior from earlier MariaDB or @@ -713,6 +728,7 @@ The following specify which files/extra groups are read (specified before remain ZERO_DATE_TIME_CAST, UTF8_IS_UTF8MB3, IGNORE_INDEX_ONLY_FOR_JOIN, COMPAT_5_1_CHECKSUM, LOCK_ALTER_TABLE_COPY + Use 'ALL' to set all combinations. --old-passwords Use old password encryption method (needed for 4.0 and older clients) --old-style-user-limits @@ -755,6 +771,10 @@ The following specify which files/extra groups are read (specified before remain --optimizer-max-sel-arg-weight=# The maximum weight of the SEL_ARG graph. Set to 0 for no limit + --optimizer-max-sel-args=# + The maximum number of SEL_ARG objects created when + optimizing a range. If more objects would be needed, the + range will not be used by the optimizer. --optimizer-prune-level=# Controls the heuristic(s) applied during query optimization to prune less-promising partial plans from @@ -1070,6 +1090,8 @@ The following specify which files/extra groups are read (specified before remain --read-rnd-buffer-size=# When reading rows in sorted order after a sort, the rows are read through this buffer to avoid a disk seeks + --redirect-url=name URL of another server to redirect clients to. Empty + string means no redirection --relay-log=name The location and name to use for relay logs. --relay-log-index=name The location and name to use for the file that keeps a @@ -1363,6 +1385,7 @@ The following specify which files/extra groups are read (specified before remain variable is empty, no conversions are allowed and it is expected that the types match exactly. Any combination of: ALL_LOSSY, ALL_NON_LOSSY + Use 'ALL' to set all combinations. --slow-launch-time=# If creating the thread takes longer than this value (in seconds), the Slow_launch_threads counter will be @@ -1393,6 +1416,7 @@ The following specify which files/extra groups are read (specified before remain NO_ENGINE_SUBSTITUTION, PAD_CHAR_TO_FULL_LENGTH, EMPTY_STRING_IS_NULL, SIMULTANEOUS_ASSIGNMENT, TIME_ROUND_FRACTIONAL + Use 'ALL' to set all combinations. --sql-safe-updates If set to 1, UPDATEs and DELETEs need either a key in the WHERE clause, or a LIMIT clause, or else they will aborted. Prevents the common mistake of accidentally @@ -1502,6 +1526,7 @@ The following specify which files/extra groups are read (specified before remain --thread-stack=# The stack size for each thread --tls-version=name TLS protocol version for secure connections.. Any combination of: TLSv1.0, TLSv1.1, TLSv1.2, TLSv1.3 + Use 'ALL' to set all combinations. --tmp-disk-table-size=# Max size for data for an internal temporary on-disk MyISAM or Aria table. @@ -1684,6 +1709,7 @@ log-slave-updates FALSE log-slow-admin-statements TRUE log-slow-disabled-statements sp log-slow-filter admin,filesort,filesort_on_disk,filesort_priority_queue,full_join,full_scan,query_cache,query_cache_miss,tmp_table,tmp_table_on_disk +log-slow-max-warnings 10 log-slow-min-examined-row-limit 0 log-slow-query FALSE log-slow-query-time 10 @@ -1740,6 +1766,7 @@ net-buffer-length 16384 net-read-timeout 30 net-retry-count 10 net-write-timeout 60 +note-verbosity basic,explain old FALSE old-mode UTF8_IS_UTF8MB3 old-passwords FALSE @@ -1753,6 +1780,7 @@ optimizer-key-copy-cost 0.015685 optimizer-key-lookup-cost 0.435777 optimizer-key-next-find-cost 0.082347 optimizer-max-sel-arg-weight 32000 +optimizer-max-sel-args 16000 optimizer-prune-level 2 optimizer-row-copy-cost 0.060866 optimizer-row-lookup-cost 0.130839 @@ -1845,6 +1873,7 @@ read-binlog-speed-limit 0 read-buffer-size 131072 read-only FALSE read-rnd-buffer-size 262144 +redirect-url relay-log (No default value) relay-log-index (No default value) relay-log-info-file relay-log.info @@ -1876,7 +1905,7 @@ secure-timestamp NO server-id 1 session-track-schema TRUE session-track-state-change FALSE -session-track-system-variables autocommit,character_set_client,character_set_connection,character_set_results,time_zone +session-track-system-variables autocommit,character_set_client,character_set_connection,character_set_results,redirect_url,time_zone session-track-transaction-info OFF show-slave-auth-info FALSE silent-startup FALSE diff --git a/mysql-test/main/mysqldump-system,win.rdiff b/mysql-test/main/mysqldump-system,win.rdiff index 57ce772a452..50c08438dcf 100644 --- a/mysql-test/main/mysqldump-system,win.rdiff +++ b/mysql-test/main/mysqldump-system,win.rdiff @@ -3,24 +3,24 @@ @@ -449,9 +449,9 @@ Table Checksum mysql.roles_mapping 2510045525 - mysql.time_zone_transition 3895294076 + mysql.time_zone_transition 3719776009 -mysql.plugin 1587119305 +mysql.plugin 2184891911 mysql.servers 2079085450 -mysql.func 3241572444 +mysql.func 310494789 - mysql.innodb_table_stats 347867921 - mysql.table_stats 664320059 + mysql.innodb_table_stats 1285726777 + mysql.table_stats 2836905944 # Opps.... @@ -484,9 +484,9 @@ Table Checksum mysql.roles_mapping 2510045525 - mysql.time_zone_transition 3895294076 + mysql.time_zone_transition 3719776009 -mysql.plugin 1587119305 +mysql.plugin 2184891911 mysql.servers 2079085450 -mysql.func 3241572444 +mysql.func 310494789 - mysql.innodb_table_stats 347867921 - mysql.table_stats 664320059 + mysql.innodb_table_stats 1285726777 + mysql.table_stats 2836905944 DROP FUNCTION IF EXISTS metaphon; diff --git a/mysql-test/main/mysqldump-system.result b/mysql-test/main/mysqldump-system.result index 559f6f29f44..7281031b0fa 100644 --- a/mysql-test/main/mysqldump-system.result +++ b/mysql-test/main/mysqldump-system.result @@ -96,29 +96,29 @@ USE mysql; LOCK TABLES `column_stats` WRITE; /*!40000 ALTER TABLE `column_stats` DISABLE KEYS */; REPLACE INTO `column_stats` VALUES -('mysql','tz','Time_zone_id','1','5',0.0000,4.0000,98.2500,4,'JSON_HB','{\"target_histogram_size\": 254, \"collected_at\": \"2022-01-07 07:07:00\", \"collected_by\": \"version\", \"histogram_hb\": [{\"start\": \"1\", \"size\": 0.340966921, \"ndv\": 1}, {\"start\": \"3\", \"size\": 0.328244275, \"ndv\": 1}, {\"start\": \"4\", \"size\": 0.328244275, \"ndv\": 1}, {\"start\": \"5\", \"end\": \"5\", \"size\": 0.002544529, \"ndv\": 1}]}'); +('mysql','tz','Time_zone_id','1','6',0.0000,4.0000,78.8000,4,'JSON_HB','{\"target_histogram_size\": 254, \"collected_at\": \"2022-01-07 07:07:00\", \"collected_by\": \"version\", \"histogram_hb\": [{\"start\": \"1\", \"size\": 0.340101523, \"ndv\": 1}, {\"start\": \"3\", \"size\": 0.327411168, \"ndv\": 1}, {\"start\": \"4\", \"size\": 0.327411168, \"ndv\": 1}, {\"start\": \"5\", \"end\": \"6\", \"size\": 0.005076142, \"ndv\": 2}]}'); /*!40000 ALTER TABLE `column_stats` ENABLE KEYS */; UNLOCK TABLES; LOCK TABLES `index_stats` WRITE; /*!40000 ALTER TABLE `index_stats` DISABLE KEYS */; REPLACE INTO `index_stats` VALUES -('mysql','tz','PRIMARY',1,98.2500); +('mysql','tz','PRIMARY',1,78.8000); /*!40000 ALTER TABLE `index_stats` ENABLE KEYS */; UNLOCK TABLES; LOCK TABLES `table_stats` WRITE; /*!40000 ALTER TABLE `table_stats` DISABLE KEYS */; REPLACE INTO `table_stats` VALUES -('mysql','tz',393); +('mysql','tz',394); /*!40000 ALTER TABLE `table_stats` ENABLE KEYS */; UNLOCK TABLES; LOCK TABLES `innodb_index_stats` WRITE; /*!40000 ALTER TABLE `innodb_index_stats` DISABLE KEYS */; REPLACE INTO `innodb_index_stats` VALUES -('mysql','tz','PRIMARY','2019-12-31 21:00:00','n_diff_pfx01',4,1,'Time_zone_id'), -('mysql','tz','PRIMARY','2019-12-31 21:00:00','n_diff_pfx02',393,1,'Time_zone_id,Transition_time'), +('mysql','tz','PRIMARY','2019-12-31 21:00:00','n_diff_pfx01',5,1,'Time_zone_id'), +('mysql','tz','PRIMARY','2019-12-31 21:00:00','n_diff_pfx02',394,1,'Time_zone_id,Transition_time'), ('mysql','tz','PRIMARY','2019-12-31 21:00:00','n_leaf_pages',1,NULL,'Number of leaf pages in the index'), ('mysql','tz','PRIMARY','2019-12-31 21:00:00','size',1,NULL,'Number of pages in the index'); /*!40000 ALTER TABLE `innodb_index_stats` ENABLE KEYS */; @@ -127,7 +127,7 @@ UNLOCK TABLES; LOCK TABLES `innodb_table_stats` WRITE; /*!40000 ALTER TABLE `innodb_table_stats` DISABLE KEYS */; REPLACE INTO `innodb_table_stats` VALUES -('mysql','tz','2019-12-31 21:00:00',393,1,0); +('mysql','tz','2019-12-31 21:00:00',394,1,0); /*!40000 ALTER TABLE `innodb_table_stats` ENABLE KEYS */; UNLOCK TABLES; @@ -140,7 +140,8 @@ REPLACE INTO `time_zone` VALUES (2,'N'), (3,'N'), (4,'Y'), -(5,'N'); +(5,'N'), +(6,'Y'); /*!40000 ALTER TABLE `time_zone` ENABLE KEYS */; UNLOCK TABLES; @@ -148,6 +149,7 @@ LOCK TABLES `time_zone_name` WRITE; /*!40000 ALTER TABLE `time_zone_name` DISABLE KEYS */; REPLACE INTO `time_zone_name` VALUES ('Europe/Moscow',3), +('India/Kolkata',6), ('Japan',5), ('leap/Europe/Moscow',4), ('MET',1), @@ -159,6 +161,7 @@ UNLOCK TABLES; LOCK TABLES `time_zone_leap_second` WRITE; /*!40000 ALTER TABLE `time_zone_leap_second` DISABLE KEYS */; REPLACE INTO `time_zone_leap_second` VALUES +(174834660,1), (78796800,1), (94694401,2), (126230402,3), @@ -579,7 +582,8 @@ REPLACE INTO `time_zone_transition` VALUES (4,2108588422,8), (4,2121894022,9), (4,2140038022,8), -(5,-1009875600,1); +(5,-1009875600,1), +(6,174834660,1); /*!40000 ALTER TABLE `time_zone_transition` ENABLE KEYS */; UNLOCK TABLES; @@ -616,7 +620,8 @@ REPLACE INTO `time_zone_transition_type` VALUES (4,10,10800,1,'EEST'), (4,11,7200,0,'EET'), (5,0,32400,0,'CJT'), -(5,1,32400,0,'JST'); +(5,1,32400,0,'JST'), +(6,1,19800,0,'IST'); /*!40000 ALTER TABLE `time_zone_transition_type` ENABLE KEYS */; UNLOCK TABLES; /*!40103 SET TIME_ZONE=@OLD_TIME_ZONE */; @@ -710,29 +715,29 @@ USE mysql; LOCK TABLES `column_stats` WRITE; /*!40000 ALTER TABLE `column_stats` DISABLE KEYS */; REPLACE INTO `column_stats` VALUES -('mysql','tz','Time_zone_id','1','5',0.0000,4.0000,98.2500,4,'JSON_HB','{\"target_histogram_size\": 254, \"collected_at\": \"2022-01-07 07:07:00\", \"collected_by\": \"version\", \"histogram_hb\": [{\"start\": \"1\", \"size\": 0.340966921, \"ndv\": 1}, {\"start\": \"3\", \"size\": 0.328244275, \"ndv\": 1}, {\"start\": \"4\", \"size\": 0.328244275, \"ndv\": 1}, {\"start\": \"5\", \"end\": \"5\", \"size\": 0.002544529, \"ndv\": 1}]}'); +('mysql','tz','Time_zone_id','1','6',0.0000,4.0000,78.8000,4,'JSON_HB','{\"target_histogram_size\": 254, \"collected_at\": \"2022-01-07 07:07:00\", \"collected_by\": \"version\", \"histogram_hb\": [{\"start\": \"1\", \"size\": 0.340101523, \"ndv\": 1}, {\"start\": \"3\", \"size\": 0.327411168, \"ndv\": 1}, {\"start\": \"4\", \"size\": 0.327411168, \"ndv\": 1}, {\"start\": \"5\", \"end\": \"6\", \"size\": 0.005076142, \"ndv\": 2}]}'); /*!40000 ALTER TABLE `column_stats` ENABLE KEYS */; UNLOCK TABLES; LOCK TABLES `index_stats` WRITE; /*!40000 ALTER TABLE `index_stats` DISABLE KEYS */; REPLACE INTO `index_stats` VALUES -('mysql','tz','PRIMARY',1,98.2500); +('mysql','tz','PRIMARY',1,78.8000); /*!40000 ALTER TABLE `index_stats` ENABLE KEYS */; UNLOCK TABLES; LOCK TABLES `table_stats` WRITE; /*!40000 ALTER TABLE `table_stats` DISABLE KEYS */; REPLACE INTO `table_stats` VALUES -('mysql','tz',393); +('mysql','tz',394); /*!40000 ALTER TABLE `table_stats` ENABLE KEYS */; UNLOCK TABLES; LOCK TABLES `innodb_index_stats` WRITE; /*!40000 ALTER TABLE `innodb_index_stats` DISABLE KEYS */; REPLACE INTO `innodb_index_stats` VALUES -('mysql','tz','PRIMARY','2019-12-31 21:00:00','n_diff_pfx01',4,1,'Time_zone_id'), -('mysql','tz','PRIMARY','2019-12-31 21:00:00','n_diff_pfx02',393,1,'Time_zone_id,Transition_time'), +('mysql','tz','PRIMARY','2019-12-31 21:00:00','n_diff_pfx01',5,1,'Time_zone_id'), +('mysql','tz','PRIMARY','2019-12-31 21:00:00','n_diff_pfx02',394,1,'Time_zone_id,Transition_time'), ('mysql','tz','PRIMARY','2019-12-31 21:00:00','n_leaf_pages',1,NULL,'Number of leaf pages in the index'), ('mysql','tz','PRIMARY','2019-12-31 21:00:00','size',1,NULL,'Number of pages in the index'); /*!40000 ALTER TABLE `innodb_index_stats` ENABLE KEYS */; @@ -741,7 +746,7 @@ UNLOCK TABLES; LOCK TABLES `innodb_table_stats` WRITE; /*!40000 ALTER TABLE `innodb_table_stats` DISABLE KEYS */; REPLACE INTO `innodb_table_stats` VALUES -('mysql','tz','2019-12-31 21:00:00',393,1,0); +('mysql','tz','2019-12-31 21:00:00',394,1,0); /*!40000 ALTER TABLE `innodb_table_stats` ENABLE KEYS */; UNLOCK TABLES; @@ -754,7 +759,8 @@ REPLACE INTO `time_zone` VALUES (2,'N'), (3,'N'), (4,'Y'), -(5,'N'); +(5,'N'), +(6,'Y'); /*!40000 ALTER TABLE `time_zone` ENABLE KEYS */; UNLOCK TABLES; @@ -762,6 +768,7 @@ LOCK TABLES `time_zone_name` WRITE; /*!40000 ALTER TABLE `time_zone_name` DISABLE KEYS */; REPLACE INTO `time_zone_name` VALUES ('Europe/Moscow',3), +('India/Kolkata',6), ('Japan',5), ('leap/Europe/Moscow',4), ('MET',1), @@ -773,6 +780,7 @@ UNLOCK TABLES; LOCK TABLES `time_zone_leap_second` WRITE; /*!40000 ALTER TABLE `time_zone_leap_second` DISABLE KEYS */; REPLACE INTO `time_zone_leap_second` VALUES +(174834660,1), (78796800,1), (94694401,2), (126230402,3), @@ -1193,7 +1201,8 @@ REPLACE INTO `time_zone_transition` VALUES (4,2108588422,8), (4,2121894022,9), (4,2140038022,8), -(5,-1009875600,1); +(5,-1009875600,1), +(6,174834660,1); /*!40000 ALTER TABLE `time_zone_transition` ENABLE KEYS */; UNLOCK TABLES; @@ -1230,7 +1239,8 @@ REPLACE INTO `time_zone_transition_type` VALUES (4,10,10800,1,'EEST'), (4,11,7200,0,'EET'), (5,0,32400,0,'CJT'), -(5,1,32400,0,'JST'); +(5,1,32400,0,'JST'), +(6,1,19800,0,'IST'); /*!40000 ALTER TABLE `time_zone_transition_type` ENABLE KEYS */; UNLOCK TABLES; /*!40103 SET TIME_ZONE=@OLD_TIME_ZONE */; @@ -1301,29 +1311,29 @@ USE mysql; LOCK TABLES `column_stats` WRITE; /*!40000 ALTER TABLE `column_stats` DISABLE KEYS */; INSERT IGNORE INTO `column_stats` VALUES -('mysql','tz','Time_zone_id','1','5',0.0000,4.0000,98.2500,4,'JSON_HB','{\"target_histogram_size\": 254, \"collected_at\": \"2022-01-07 07:07:00\", \"collected_by\": \"version\", \"histogram_hb\": [{\"start\": \"1\", \"size\": 0.340966921, \"ndv\": 1}, {\"start\": \"3\", \"size\": 0.328244275, \"ndv\": 1}, {\"start\": \"4\", \"size\": 0.328244275, \"ndv\": 1}, {\"start\": \"5\", \"end\": \"5\", \"size\": 0.002544529, \"ndv\": 1}]}'); +('mysql','tz','Time_zone_id','1','6',0.0000,4.0000,78.8000,4,'JSON_HB','{\"target_histogram_size\": 254, \"collected_at\": \"2022-01-07 07:07:00\", \"collected_by\": \"version\", \"histogram_hb\": [{\"start\": \"1\", \"size\": 0.340101523, \"ndv\": 1}, {\"start\": \"3\", \"size\": 0.327411168, \"ndv\": 1}, {\"start\": \"4\", \"size\": 0.327411168, \"ndv\": 1}, {\"start\": \"5\", \"end\": \"6\", \"size\": 0.005076142, \"ndv\": 2}]}'); /*!40000 ALTER TABLE `column_stats` ENABLE KEYS */; UNLOCK TABLES; LOCK TABLES `index_stats` WRITE; /*!40000 ALTER TABLE `index_stats` DISABLE KEYS */; INSERT IGNORE INTO `index_stats` VALUES -('mysql','tz','PRIMARY',1,98.2500); +('mysql','tz','PRIMARY',1,78.8000); /*!40000 ALTER TABLE `index_stats` ENABLE KEYS */; UNLOCK TABLES; LOCK TABLES `table_stats` WRITE; /*!40000 ALTER TABLE `table_stats` DISABLE KEYS */; INSERT IGNORE INTO `table_stats` VALUES -('mysql','tz',393); +('mysql','tz',394); /*!40000 ALTER TABLE `table_stats` ENABLE KEYS */; UNLOCK TABLES; LOCK TABLES `innodb_index_stats` WRITE; /*!40000 ALTER TABLE `innodb_index_stats` DISABLE KEYS */; INSERT IGNORE INTO `innodb_index_stats` VALUES -('mysql','tz','PRIMARY','2019-12-31 21:00:00','n_diff_pfx01',4,1,'Time_zone_id'), -('mysql','tz','PRIMARY','2019-12-31 21:00:00','n_diff_pfx02',393,1,'Time_zone_id,Transition_time'), +('mysql','tz','PRIMARY','2019-12-31 21:00:00','n_diff_pfx01',5,1,'Time_zone_id'), +('mysql','tz','PRIMARY','2019-12-31 21:00:00','n_diff_pfx02',394,1,'Time_zone_id,Transition_time'), ('mysql','tz','PRIMARY','2019-12-31 21:00:00','n_leaf_pages',1,NULL,'Number of leaf pages in the index'), ('mysql','tz','PRIMARY','2019-12-31 21:00:00','size',1,NULL,'Number of pages in the index'); /*!40000 ALTER TABLE `innodb_index_stats` ENABLE KEYS */; @@ -1332,7 +1342,7 @@ UNLOCK TABLES; LOCK TABLES `innodb_table_stats` WRITE; /*!40000 ALTER TABLE `innodb_table_stats` DISABLE KEYS */; INSERT IGNORE INTO `innodb_table_stats` VALUES -('mysql','tz','2019-12-31 21:00:00',393,1,0); +('mysql','tz','2019-12-31 21:00:00',394,1,0); /*!40000 ALTER TABLE `innodb_table_stats` ENABLE KEYS */; UNLOCK TABLES; @@ -1345,7 +1355,8 @@ INSERT IGNORE INTO `time_zone` VALUES (2,'N'), (3,'N'), (4,'Y'), -(5,'N'); +(5,'N'), +(6,'Y'); /*!40000 ALTER TABLE `time_zone` ENABLE KEYS */; UNLOCK TABLES; @@ -1353,6 +1364,7 @@ LOCK TABLES `time_zone_name` WRITE; /*!40000 ALTER TABLE `time_zone_name` DISABLE KEYS */; INSERT IGNORE INTO `time_zone_name` VALUES ('Europe/Moscow',3), +('India/Kolkata',6), ('Japan',5), ('leap/Europe/Moscow',4), ('MET',1), @@ -1364,6 +1376,7 @@ UNLOCK TABLES; LOCK TABLES `time_zone_leap_second` WRITE; /*!40000 ALTER TABLE `time_zone_leap_second` DISABLE KEYS */; INSERT IGNORE INTO `time_zone_leap_second` VALUES +(174834660,1), (78796800,1), (94694401,2), (126230402,3), @@ -1784,7 +1797,8 @@ INSERT IGNORE INTO `time_zone_transition` VALUES (4,2108588422,8), (4,2121894022,9), (4,2140038022,8), -(5,-1009875600,1); +(5,-1009875600,1), +(6,174834660,1); /*!40000 ALTER TABLE `time_zone_transition` ENABLE KEYS */; UNLOCK TABLES; @@ -1821,7 +1835,8 @@ INSERT IGNORE INTO `time_zone_transition_type` VALUES (4,10,10800,1,'EEST'), (4,11,7200,0,'EET'), (5,0,32400,0,'CJT'), -(5,1,32400,0,'JST'); +(5,1,32400,0,'JST'), +(6,1,19800,0,'IST'); /*!40000 ALTER TABLE `time_zone_transition_type` ENABLE KEYS */; UNLOCK TABLES; /*!40103 SET TIME_ZONE=@OLD_TIME_ZONE */; @@ -1845,12 +1860,12 @@ CHECKSUM TABLE mysql.roles_mapping, mysql.time_zone_transition, mysql.plugin, mysql.servers, mysql.func, mysql.innodb_table_stats, mysql.table_stats; Table Checksum mysql.roles_mapping 2510045525 -mysql.time_zone_transition 3895294076 +mysql.time_zone_transition 3719776009 mysql.plugin 1587119305 mysql.servers 2079085450 mysql.func 3241572444 -mysql.innodb_table_stats 347867921 -mysql.table_stats 664320059 +mysql.innodb_table_stats 1285726777 +mysql.table_stats 2836905944 # Opps.... CREATE USER mariadb_test_restore IDENTIFIED BY 'getitback'; GRANT ALL ON *.* TO mariadb_test_restore WITH GRANT OPTION; @@ -1875,17 +1890,17 @@ Host User Priv localhost mariadb.sys {"access":0,"version_id":VERSION,"plugin":"mysql_native_password","authentication_string":"","password_last_changed":NOW,"password_lifetime":-1,"default_role":""} role_1 {"access":16384,"version_id":VERSION,"is_role":true} role_2 {"access":0,"version_id":VERSION,"is_role":true} -localhost root {"access":549755813887,"version_id":VERSION,"plugin":"mysql_native_password","authentication_string":"","password_last_changed":NOW,"default_role":""} +localhost root {"access":1099511627775,"version_id":VERSION,"plugin":"mysql_native_password","authentication_string":"","password_last_changed":NOW,"default_role":""} CHECKSUM TABLE mysql.roles_mapping, mysql.time_zone_transition, mysql.plugin, mysql.servers, mysql.func, mysql.innodb_table_stats, mysql.table_stats; Table Checksum mysql.roles_mapping 2510045525 -mysql.time_zone_transition 3895294076 +mysql.time_zone_transition 3719776009 mysql.plugin 1587119305 mysql.servers 2079085450 mysql.func 3241572444 -mysql.innodb_table_stats 347867921 -mysql.table_stats 664320059 +mysql.innodb_table_stats 1285726777 +mysql.table_stats 2836905944 DROP FUNCTION IF EXISTS metaphon; DROP SERVER s1; DELETE FROM mysql.column_stats WHERE db_name='mysql' and table_name in ('tz', 'gtid_slave_pos'); diff --git a/mysql-test/main/mysqldump.result b/mysql-test/main/mysqldump.result index 59b9875507d..c99f906080f 100644 --- a/mysql-test/main/mysqldump.result +++ b/mysql-test/main/mysqldump.result @@ -3941,6 +3941,8 @@ use test; create database mysqldump_test_db; grant all privileges on mysqldump_test_db.* to user1; grant all privileges on mysqldump_test_db.* to user2; +revoke SHOW CREATE ROUTINE on mysqldump_test_db.* from user1; +revoke SHOW CREATE ROUTINE on mysqldump_test_db.* from user2; connect user27293,localhost,user1,,mysqldump_test_db,$MASTER_MYPORT,$MASTER_MYSOCK; connection user27293; create procedure mysqldump_test_db.sp1() select 'hello'; @@ -5179,6 +5181,7 @@ END # Test to check 'Insufficient privileges' error. GRANT ALL PRIVILEGES ON BUG52792.* TO user1; +REVOKE SHOW CREATE ROUTINE ON BUG52792.* FROM user1; connect conn_1, localhost, user1, , BUG52792, $MASTER_MYPORT, $MASTER_MYSOCK; connection conn_1; # Running 'replace_regex on timestamp' @@ -5399,15 +5402,15 @@ slow_log CREATE TABLE `slow_log` ( `user_host` mediumtext NOT NULL, `query_time` time(6) NOT NULL, `lock_time` time(6) NOT NULL, - `rows_sent` int(11) NOT NULL, - `rows_examined` int(11) NOT NULL, + `rows_sent` bigint(20) unsigned NOT NULL, + `rows_examined` bigint(20) unsigned NOT NULL, `db` varchar(512) NOT NULL, `last_insert_id` int(11) NOT NULL, `insert_id` int(11) NOT NULL, `server_id` int(10) unsigned NOT NULL, `sql_text` mediumtext NOT NULL, `thread_id` bigint(21) unsigned NOT NULL, - `rows_affected` int(11) NOT NULL + `rows_affected` bigint(20) unsigned NOT NULL ) ENGINE=CSV DEFAULT CHARSET=utf8mb3 COLLATE=utf8mb3_general_ci COMMENT='Slow log' SET @@global.log_output= @old_log_output_state; SET @@global.slow_query_log= @old_slow_query_log_state; @@ -5890,15 +5893,15 @@ CREATE TABLE IF NOT EXISTS `slow_log` ( `user_host` mediumtext NOT NULL, `query_time` time(6) NOT NULL, `lock_time` time(6) NOT NULL, - `rows_sent` int(11) NOT NULL, - `rows_examined` int(11) NOT NULL, + `rows_sent` bigint(20) unsigned NOT NULL, + `rows_examined` bigint(20) unsigned NOT NULL, `db` varchar(512) NOT NULL, `last_insert_id` int(11) NOT NULL, `insert_id` int(11) NOT NULL, `server_id` int(10) unsigned NOT NULL, `sql_text` mediumtext NOT NULL, `thread_id` bigint(21) unsigned NOT NULL, - `rows_affected` int(11) NOT NULL + `rows_affected` bigint(20) unsigned NOT NULL ) ENGINE=CSV DEFAULT CHARSET=utf8mb3 COLLATE=utf8mb3_general_ci COMMENT='Slow log'; /*!40101 SET character_set_client = @saved_cs_client */; DROP TABLE IF EXISTS `innodb_index_stats`; @@ -5985,15 +5988,15 @@ CREATE TABLE IF NOT EXISTS `slow_log` ( `user_host` mediumtext NOT NULL, `query_time` time(6) NOT NULL, `lock_time` time(6) NOT NULL, - `rows_sent` int(11) NOT NULL, - `rows_examined` int(11) NOT NULL, + `rows_sent` bigint(20) unsigned NOT NULL, + `rows_examined` bigint(20) unsigned NOT NULL, `db` varchar(512) NOT NULL, `last_insert_id` int(11) NOT NULL, `insert_id` int(11) NOT NULL, `server_id` int(10) unsigned NOT NULL, `sql_text` mediumtext NOT NULL, `thread_id` bigint(21) unsigned NOT NULL, - `rows_affected` int(11) NOT NULL + `rows_affected` bigint(20) unsigned NOT NULL ) ENGINE=CSV DEFAULT CHARSET=utf8mb3 COLLATE=utf8mb3_general_ci COMMENT='Slow log'; /*!40101 SET character_set_client = @saved_cs_client */; DROP TABLE IF EXISTS `innodb_index_stats`; @@ -6090,15 +6093,15 @@ CREATE TABLE IF NOT EXISTS `slow_log` ( `user_host` mediumtext NOT NULL, `query_time` time(6) NOT NULL, `lock_time` time(6) NOT NULL, - `rows_sent` int(11) NOT NULL, - `rows_examined` int(11) NOT NULL, + `rows_sent` bigint(20) unsigned NOT NULL, + `rows_examined` bigint(20) unsigned NOT NULL, `db` varchar(512) NOT NULL, `last_insert_id` int(11) NOT NULL, `insert_id` int(11) NOT NULL, `server_id` int(10) unsigned NOT NULL, `sql_text` mediumtext NOT NULL, `thread_id` bigint(21) unsigned NOT NULL, - `rows_affected` int(11) NOT NULL + `rows_affected` bigint(20) unsigned NOT NULL ) ENGINE=CSV DEFAULT CHARSET=utf8mb3 COLLATE=utf8mb3_general_ci COMMENT='Slow log'; /*!40101 SET character_set_client = @saved_cs_client */; DROP TABLE IF EXISTS `innodb_index_stats`; @@ -6550,15 +6553,15 @@ DROP TABLE IF EXISTS mysql.column_stats; - - + + - + diff --git a/mysql-test/main/mysqldump.test b/mysql-test/main/mysqldump.test index 1d479dde723..707f12b2083 100644 --- a/mysql-test/main/mysqldump.test +++ b/mysql-test/main/mysqldump.test @@ -1602,6 +1602,8 @@ create database mysqldump_test_db; grant all privileges on mysqldump_test_db.* to user1; grant all privileges on mysqldump_test_db.* to user2; +revoke SHOW CREATE ROUTINE on mysqldump_test_db.* from user1; +revoke SHOW CREATE ROUTINE on mysqldump_test_db.* from user2; connect (user27293,localhost,user1,,mysqldump_test_db,$MASTER_MYPORT,$MASTER_MYSOCK); connection user27293; @@ -2334,6 +2336,7 @@ CREATE VIEW v2 AS SELECT * FROM t2; --echo GRANT ALL PRIVILEGES ON BUG52792.* TO user1; +REVOKE SHOW CREATE ROUTINE ON BUG52792.* FROM user1; connect (conn_1, localhost, user1, , BUG52792, $MASTER_MYPORT, $MASTER_MYSOCK); connection conn_1; diff --git a/mysql-test/main/no-threads-master.opt b/mysql-test/main/no-threads.opt similarity index 100% rename from mysql-test/main/no-threads-master.opt rename to mysql-test/main/no-threads.opt diff --git a/mysql-test/main/no-threads.test b/mysql-test/main/no-threads.test index c1a608a57e6..8235ff67284 100644 --- a/mysql-test/main/no-threads.test +++ b/mysql-test/main/no-threads.test @@ -2,7 +2,6 @@ # an additional util connection and other statistics data -- source include/no_view_protocol.inc ---source include/one_thread_per_connection.inc # # Test the --thread-handler=no-threads option # diff --git a/mysql-test/main/null_key.result b/mysql-test/main/null_key.result index cee3484a304..0b1446fd72e 100644 --- a/mysql-test/main/null_key.result +++ b/mysql-test/main/null_key.result @@ -1,4 +1,5 @@ drop table if exists t1,t2; +set @@note_verbosity=replace(@@note_verbosity,"explain",""); create table t1 (a int, b int not null,unique key (a,b),index(b)) engine=myisam; insert ignore into t1 values (1,1),(2,2),(3,3),(4,4),(5,5),(6,6),(null,7),(9,9),(8,8),(7,7),(null,9),(null,9),(6,6); Warnings: @@ -475,3 +476,5 @@ INSERT INTO t1 VALUES ('9','k'),(NULL,'r'); SELECT * FROM t1 WHERE (f3 = 83) OR (f10 = 'z' AND f3 IS NULL); f3 f10 DROP TABLE t1; +## end of 10.6 tests +set @@note_verbosity=default; diff --git a/mysql-test/main/null_key.test b/mysql-test/main/null_key.test index 26ac9a081f9..7fc21ee1e1d 100644 --- a/mysql-test/main/null_key.test +++ b/mysql-test/main/null_key.test @@ -5,6 +5,9 @@ drop table if exists t1,t2; --enable_warnings +# Disable wrong key warnings for this test (to test @@note_verbosity usage) +set @@note_verbosity=replace(@@note_verbosity,"explain",""); + create table t1 (a int, b int not null,unique key (a,b),index(b)) engine=myisam; insert ignore into t1 values (1,1),(2,2),(3,3),(4,4),(5,5),(6,6),(null,7),(9,9),(8,8),(7,7),(null,9),(null,9),(6,6); explain select * from t1 where a is null; @@ -288,3 +291,6 @@ INSERT INTO t1 VALUES ('9','k'),(NULL,'r'); SELECT * FROM t1 WHERE (f3 = 83) OR (f10 = 'z' AND f3 IS NULL); DROP TABLE t1; +--echo ## end of 10.6 tests + +set @@note_verbosity=default; diff --git a/mysql-test/main/order_by_pack_big.test b/mysql-test/main/order_by_pack_big.test index 5e39d9f2988..ec8e0c12c54 100644 --- a/mysql-test/main/order_by_pack_big.test +++ b/mysql-test/main/order_by_pack_big.test @@ -112,9 +112,12 @@ set sort_buffer_size=262144*10; --source include/analyze-format.inc eval analyze format=json $query; flush status; +# Enable view-protocol after fix MDEV-27871 +--disable_view_protocol --disable_ps2_protocol eval $query; --enable_ps2_protocol +--enable_view_protocol show status like '%sort%'; set sort_buffer_size=default; @@ -126,9 +129,12 @@ set sort_buffer_size=32768; --source include/analyze-format.inc eval analyze format=json $query; flush status; +# Enable view-protocol after fix MDEV-27871 +--disable_view_protocol --disable_ps2_protocol eval $query; --enable_ps2_protocol +--enable_view_protocol show status like '%sort%'; set sort_buffer_size=default; diff --git a/mysql-test/main/partition.result b/mysql-test/main/partition.result index 9155f90d781..3cb9b3043cd 100644 --- a/mysql-test/main/partition.result +++ b/mysql-test/main/partition.result @@ -2859,6 +2859,19 @@ id select_type table type possible_keys key key_len ref rows Extra set optimizer_switch=@tmp_os; drop table t1,t2,t3; # +# MDEV-32388 MSAN / Valgrind errors in +# Item_func_like::get_mm_leaf upon query from partitioned table +# +CREATE TABLE t1 (a INT) PARTITION BY HASH(a) PARTITIONS 2; +INSERT INTO t1 VALUES (1),(2); +SELECT * FROM t1 WHERE a LIKE '1'; +a +1 +DROP TABLE t1; +# +# End of 10.6 tests +# +# # MDEV-31494 Server crashes in ha_partition::index_blocks / # get_key_scans_params # diff --git a/mysql-test/main/partition.test b/mysql-test/main/partition.test index a6b583798ce..ca22e77971b 100644 --- a/mysql-test/main/partition.test +++ b/mysql-test/main/partition.test @@ -3067,6 +3067,20 @@ set optimizer_switch=@tmp_os; drop table t1,t2,t3; +--echo # +--echo # MDEV-32388 MSAN / Valgrind errors in +--echo # Item_func_like::get_mm_leaf upon query from partitioned table +--echo # + +CREATE TABLE t1 (a INT) PARTITION BY HASH(a) PARTITIONS 2; +INSERT INTO t1 VALUES (1),(2); +SELECT * FROM t1 WHERE a LIKE '1'; +DROP TABLE t1; + +--echo # +--echo # End of 10.6 tests +--echo # + --echo # --echo # MDEV-31494 Server crashes in ha_partition::index_blocks / --echo # get_key_scans_params diff --git a/mysql-test/main/partition_explicit_prune.result b/mysql-test/main/partition_explicit_prune.result index f4436c5040c..d31790e4433 100644 --- a/mysql-test/main/partition_explicit_prune.result +++ b/mysql-test/main/partition_explicit_prune.result @@ -350,7 +350,6 @@ WHERE VARIABLE_NAME LIKE 'HANDLER_%' AND VARIABLE_VALUE > 0; VARIABLE_NAME VARIABLE_VALUE HANDLER_COMMIT 1 HANDLER_READ_FIRST 1 -HANDLER_READ_KEY 8 HANDLER_TMP_WRITE 24 # Should be 1 commit # 4 locks (1 ha_partition + 1 ha_innobase) x 2 (lock/unlock) @@ -775,7 +774,7 @@ SELECT * FROM INFORMATION_SCHEMA.SESSION_STATUS WHERE VARIABLE_NAME LIKE 'HANDLER_%' AND VARIABLE_VALUE > 0; VARIABLE_NAME VARIABLE_VALUE HANDLER_COMMIT 1 -HANDLER_READ_KEY 8 +HANDLER_READ_KEY 6 HANDLER_READ_RND_NEXT 2 HANDLER_TMP_WRITE 24 HANDLER_UPDATE 2 diff --git a/mysql-test/main/partition_innodb2.result b/mysql-test/main/partition_innodb2.result index 4476eb91447..4d75b468259 100644 --- a/mysql-test/main/partition_innodb2.result +++ b/mysql-test/main/partition_innodb2.result @@ -18,7 +18,7 @@ mod(seq, 10), seq from seq_1_to_50; explain delete t1, t2 from t1, t2 where t1.a=t2.a; id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 ALL NULL NULL NULL NULL 4 Using where -1 SIMPLE t2 ref a a 5 test.t1.a 1 +1 SIMPLE t1 ALL NULL NULL NULL NULL # Using where +1 SIMPLE t2 ref a a 5 test.t1.a # delete t1, t2 from t1, t2 where t1.a=t2.a; drop table t1,t2; diff --git a/mysql-test/main/partition_innodb2.test b/mysql-test/main/partition_innodb2.test index 7581c5db4ca..e2089ae3e8a 100644 --- a/mysql-test/main/partition_innodb2.test +++ b/mysql-test/main/partition_innodb2.test @@ -23,6 +23,7 @@ create table t2 ( insert into t2 select mod(seq, 10), seq from seq_1_to_50; +--replace_column 9 # explain delete t1, t2 from t1, t2 where t1.a=t2.a; delete t1, t2 from t1, t2 where t1.a=t2.a; diff --git a/mysql-test/main/range.result b/mysql-test/main/range.result index 138aeff1fde..e14b78baf32 100644 --- a/mysql-test/main/range.result +++ b/mysql-test/main/range.result @@ -642,6 +642,8 @@ id select_type table type possible_keys key key_len ref rows Extra explain select * from t1 where a='aaa' collate latin1_german1_ci; id select_type table type possible_keys key key_len ref rows Extra 1 SIMPLE t1 ALL a NULL NULL NULL 9 Using where +Warnings: +Note 1105 Cannot use key `a` part[0] for lookup: `test`.`t1`.`a` of collation `latin1_swedish_ci` = "'aaa' collate latin1_german1_ci" of collation `latin1_german1_ci` drop table t1; CREATE TABLE t1 ( `CLIENT` char(3) character set latin1 collate latin1_bin NOT NULL default '000', @@ -2236,6 +2238,8 @@ INSERT INTO t2 VALUES ('2001-01-01 11:22:33'); EXPLAIN SELECT * FROM t2 WHERE b=CAST('2001-01-01' AS DATE); id select_type table type possible_keys key key_len ref rows Extra 1 SIMPLE t2 index b b 67 NULL 5 Using where; Using index +Warnings: +Note 1105 Cannot use key `b` part[0] for lookup: `test`.`t2`.`b` of type `varchar` = "cast('2001-01-01' as date)" of type `date` SELECT * FROM t2 WHERE b=CAST('2001-01-01' AS DATE); b 2001#01#01 @@ -2250,6 +2254,8 @@ EXPLAIN SELECT * FROM t1, t2 WHERE a=b ORDER BY BINARY a, BINARY b; id select_type table type possible_keys key key_len ref rows Extra 1 SIMPLE t1 ALL NULL NULL NULL NULL 2 Using temporary; Using filesort 1 SIMPLE t2 ALL b NULL NULL NULL 5 Range checked for each record (index map: 0x1) +Warnings: +Note 1105 Cannot use key `b` part[0] for lookup: `test`.`t2`.`b` of type `varchar` = "`t1`.`a`" of type `datetime` SELECT * FROM t1, t2 WHERE a=b ORDER BY BINARY a, BINARY b; a b 2001-01-01 00:00:00 2001#01#01 @@ -2262,6 +2268,8 @@ EXPLAIN SELECT * FROM t1, t2 WHERE b=a ORDER BY BINARY a, BINARY b; id select_type table type possible_keys key key_len ref rows Extra 1 SIMPLE t1 ALL NULL NULL NULL NULL 2 Using temporary; Using filesort 1 SIMPLE t2 ALL b NULL NULL NULL 5 Range checked for each record (index map: 0x1) +Warnings: +Note 1105 Cannot use key `b` part[0] for lookup: `test`.`t2`.`b` of type `varchar` = "`t1`.`a`" of type `datetime` SELECT * FROM t1, t2 WHERE b=a ORDER BY BINARY a, BINARY b; a b 2001-01-01 00:00:00 2001#01#01 diff --git a/mysql-test/main/range_mrr_icp.result b/mysql-test/main/range_mrr_icp.result index faaf2d233c4..a8d547f101d 100644 --- a/mysql-test/main/range_mrr_icp.result +++ b/mysql-test/main/range_mrr_icp.result @@ -645,6 +645,8 @@ id select_type table type possible_keys key key_len ref rows Extra explain select * from t1 where a='aaa' collate latin1_german1_ci; id select_type table type possible_keys key key_len ref rows Extra 1 SIMPLE t1 ALL a NULL NULL NULL 9 Using where +Warnings: +Note 1105 Cannot use key `a` part[0] for lookup: `test`.`t1`.`a` of collation `latin1_swedish_ci` = "'aaa' collate latin1_german1_ci" of collation `latin1_german1_ci` drop table t1; CREATE TABLE t1 ( `CLIENT` char(3) character set latin1 collate latin1_bin NOT NULL default '000', @@ -2239,6 +2241,8 @@ INSERT INTO t2 VALUES ('2001-01-01 11:22:33'); EXPLAIN SELECT * FROM t2 WHERE b=CAST('2001-01-01' AS DATE); id select_type table type possible_keys key key_len ref rows Extra 1 SIMPLE t2 index b b 67 NULL 5 Using where; Using index +Warnings: +Note 1105 Cannot use key `b` part[0] for lookup: `test`.`t2`.`b` of type `varchar` = "cast('2001-01-01' as date)" of type `date` SELECT * FROM t2 WHERE b=CAST('2001-01-01' AS DATE); b 2001#01#01 @@ -2253,6 +2257,8 @@ EXPLAIN SELECT * FROM t1, t2 WHERE a=b ORDER BY BINARY a, BINARY b; id select_type table type possible_keys key key_len ref rows Extra 1 SIMPLE t1 ALL NULL NULL NULL NULL 2 Using temporary; Using filesort 1 SIMPLE t2 ALL b NULL NULL NULL 5 Range checked for each record (index map: 0x1) +Warnings: +Note 1105 Cannot use key `b` part[0] for lookup: `test`.`t2`.`b` of type `varchar` = "`t1`.`a`" of type `datetime` SELECT * FROM t1, t2 WHERE a=b ORDER BY BINARY a, BINARY b; a b 2001-01-01 00:00:00 2001#01#01 @@ -2265,6 +2271,8 @@ EXPLAIN SELECT * FROM t1, t2 WHERE b=a ORDER BY BINARY a, BINARY b; id select_type table type possible_keys key key_len ref rows Extra 1 SIMPLE t1 ALL NULL NULL NULL NULL 2 Using temporary; Using filesort 1 SIMPLE t2 ALL b NULL NULL NULL 5 Range checked for each record (index map: 0x1) +Warnings: +Note 1105 Cannot use key `b` part[0] for lookup: `test`.`t2`.`b` of type `varchar` = "`t1`.`a`" of type `datetime` SELECT * FROM t1, t2 WHERE b=a ORDER BY BINARY a, BINARY b; a b 2001-01-01 00:00:00 2001#01#01 diff --git a/mysql-test/main/require_secure_transport.result b/mysql-test/main/require_secure_transport.result index 94474d0fa0e..570f868b583 100644 --- a/mysql-test/main/require_secure_transport.result +++ b/mysql-test/main/require_secure_transport.result @@ -1,8 +1,17 @@ -CREATE TABLE t1 (t int(1)); SET GLOBAL require_secure_transport=ON; -ERROR HY000: Connections using insecure transport are prohibited while --require_secure_transport=ON. +connect(localhost,root,,test,MASTER_PORT,MASTER_SOCKET); +connect without_ssl,localhost,root,,,,,TCP NOSSL; +ERROR 08004: Connections using insecure transport are prohibited while --require_secure_transport=ON. +connect with_ssl,localhost,root,,,,,TCP SSL; +SELECT (VARIABLE_VALUE <> '') AS have_ssl FROM INFORMATION_SCHEMA.SESSION_STATUS WHERE VARIABLE_NAME='Ssl_cipher'; +have_ssl +1 +disconnect with_ssl; connection default; SET GLOBAL require_secure_transport=OFF; +connect without_ssl,localhost,root,,,,,TCP NOSSL; +SELECT (VARIABLE_VALUE <> '') AS have_ssl FROM INFORMATION_SCHEMA.SESSION_STATUS WHERE VARIABLE_NAME='Ssl_cipher'; +have_ssl +0 disconnect without_ssl; connection default; -DROP TABLE t1; diff --git a/mysql-test/main/require_secure_transport.test b/mysql-test/main/require_secure_transport.test index e238e732423..fbabd7bc7a2 100644 --- a/mysql-test/main/require_secure_transport.test +++ b/mysql-test/main/require_secure_transport.test @@ -1,15 +1,18 @@ -- source include/have_ssl_communication.inc -CREATE TABLE t1 (t int(1)); SET GLOBAL require_secure_transport=ON; ---disable_query_log +--replace_result $MASTER_MYSOCK MASTER_SOCKET $MASTER_MYPORT MASTER_PORT --error ER_SECURE_TRANSPORT_REQUIRED connect without_ssl,localhost,root,,,,,TCP NOSSL; ---enable_query_log + +--replace_result $MASTER_MYSOCK MASTER_SOCKET $MASTER_MYPORT MASTER_PORT +connect with_ssl,localhost,root,,,,,TCP SSL; +SELECT (VARIABLE_VALUE <> '') AS have_ssl FROM INFORMATION_SCHEMA.SESSION_STATUS WHERE VARIABLE_NAME='Ssl_cipher'; +disconnect with_ssl; + connection default; SET GLOBAL require_secure_transport=OFF; ---disable_query_log +--replace_result $MASTER_MYSOCK MASTER_SOCKET $MASTER_MYPORT MASTER_PORT connect without_ssl,localhost,root,,,,,TCP NOSSL; ---enable_query_log +SELECT (VARIABLE_VALUE <> '') AS have_ssl FROM INFORMATION_SCHEMA.SESSION_STATUS WHERE VARIABLE_NAME='Ssl_cipher'; disconnect without_ssl; connection default; -DROP TABLE t1; diff --git a/mysql-test/main/require_secure_transport_on.opt b/mysql-test/main/require_secure_transport_on.opt new file mode 100644 index 00000000000..c774f970dfd --- /dev/null +++ b/mysql-test/main/require_secure_transport_on.opt @@ -0,0 +1 @@ +--require-secure-transport=TRUE diff --git a/mysql-test/main/require_secure_transport_on.result b/mysql-test/main/require_secure_transport_on.result new file mode 100644 index 00000000000..3ad8468bc31 --- /dev/null +++ b/mysql-test/main/require_secure_transport_on.result @@ -0,0 +1,9 @@ +connect(localhost,root,,test,MASTER_PORT,MASTER_SOCKET); +connect without_ssl,localhost,root,,,,,TCP NOSSL; +ERROR 08004: Connections using insecure transport are prohibited while --require_secure_transport=ON. +connect with_ssl,localhost,root,,,,,TCP SSL; +SELECT (VARIABLE_VALUE <> '') AS have_ssl FROM INFORMATION_SCHEMA.SESSION_STATUS WHERE VARIABLE_NAME='Ssl_cipher'; +have_ssl +1 +disconnect with_ssl; +connection default; diff --git a/mysql-test/main/require_secure_transport_on.test b/mysql-test/main/require_secure_transport_on.test new file mode 100644 index 00000000000..09db2fa0175 --- /dev/null +++ b/mysql-test/main/require_secure_transport_on.test @@ -0,0 +1,14 @@ +--source include/not_windows.inc +--source include/have_ssl_communication.inc + +--replace_result $MASTER_MYSOCK MASTER_SOCKET $MASTER_MYPORT MASTER_PORT +--error ER_SECURE_TRANSPORT_REQUIRED +connect without_ssl,localhost,root,,,,,TCP NOSSL; + +--replace_result $MASTER_MYSOCK MASTER_SOCKET $MASTER_MYPORT MASTER_PORT +connect with_ssl,localhost,root,,,,,TCP SSL; +SELECT (VARIABLE_VALUE <> '') AS have_ssl FROM INFORMATION_SCHEMA.SESSION_STATUS WHERE VARIABLE_NAME='Ssl_cipher'; +disconnect with_ssl; + +connection default; + diff --git a/mysql-test/main/set_statement.result b/mysql-test/main/set_statement.result index a1b1d3659ff..810ec32eee2 100644 --- a/mysql-test/main/set_statement.result +++ b/mysql-test/main/set_statement.result @@ -1367,4 +1367,16 @@ SET sql_mode=ORACLE; SET STATEMENT max_statement_time=30 FOR DELETE FROM mysql.user where user = 'unknown'; SET sql_mode=default; SET STATEMENT max_statement_time=30 FOR DELETE FROM mysql.user where user = 'unknown'; +# +# MDEV-17711 Assertion `arena_for_set_stmt== 0' failed in LEX::set_arena_for_set_stmt upon SET STATEMENT +# +set rand_seed1=1, rand_seed2=2; +set statement rand_seed1=4 for select 2, @@rand_seed1, @@rand_seed2; +set statement rand_seed2=5 for select 3, @@rand_seed1, @@rand_seed2 $ +2 @@rand_seed1 @@rand_seed2 +2 4 2 +3 @@rand_seed1 @@rand_seed2 +3 1 5 +# # End of 10.4 tests +# diff --git a/mysql-test/main/set_statement.test b/mysql-test/main/set_statement.test index 86a5b7a5eab..b8df5b1797d 100644 --- a/mysql-test/main/set_statement.test +++ b/mysql-test/main/set_statement.test @@ -1197,4 +1197,18 @@ SET STATEMENT max_statement_time=30 FOR DELETE FROM mysql.user where user = 'unk SET sql_mode=default; SET STATEMENT max_statement_time=30 FOR DELETE FROM mysql.user where user = 'unknown'; +--echo # +--echo # MDEV-17711 Assertion `arena_for_set_stmt== 0' failed in LEX::set_arena_for_set_stmt upon SET STATEMENT +--echo # + +--disable_ps_protocol +--delimiter $ +set rand_seed1=1, rand_seed2=2; +set statement rand_seed1=4 for select 2, @@rand_seed1, @@rand_seed2; +set statement rand_seed2=5 for select 3, @@rand_seed1, @@rand_seed2 $ +--delimiter ; +--enable_ps_protocol + +--echo # --echo # End of 10.4 tests +--echo # diff --git a/mysql-test/main/sp-security-debug.result b/mysql-test/main/sp-security-debug.result new file mode 100644 index 00000000000..6ee7f496566 --- /dev/null +++ b/mysql-test/main/sp-security-debug.result @@ -0,0 +1,294 @@ +set @@global.character_set_server=@@session.character_set_server; +# +# MDEV-29167: new db-level SHOW CREATE ROUTINE privilege +# +### +### SHOW-Like commad test +### +SET @save_sql_mode=@@sql_mode; +# +### Prepare functions for the test and SHOW-like by owner +# +create database test_db; +use test_db; +create procedure test_db.sp() select 1; +show procedure code test_db.sp; +Pos Instruction +0 stmt 0 "select 1" +CREATE FUNCTION test_db.fn() RETURNS INT RETURN 1; +show function code test_db.fn; +Pos Instruction +0 freturn int 1 +SET sql_mode=ORACLE; +CREATE PACKAGE test_db.pk AS +FUNCTION pkf() RETURN INT; +PROCEDURE pkp(); +END; +$$ +CREATE PACKAGE BODY test_db.pk AS +pkv INT:=1; +PROCEDURE pkhp() AS +BEGIN +SELECT pkv FROM DUAL; +END; +FUNCTION pkhf() RETURN INT AS +BEGIN +RETURN pkv; +END; +PROCEDURE pkp() AS +BEGIN +CALL pkhp(); +END; +FUNCTION pkf() RETURN INT AS +BEGIN +RETURN pkhf(); +END; +BEGIN +pkv:=2; +END; +$$ +SET sql_mode=@save_sql_mode; +show package code test_db.pk; +ERROR 42000: You have an error in your SQL syntax; check the manual that corresponds to your MariaDB server version for the right syntax to use near 'code test_db.pk' at line 1 +show package body code test_db.pk; +Pos Instruction +0 set pkv@0 1 +1 set pkv@0 2 +use test; +### +### Pre-"SHOW-CREATE-ROUTINE" behaviour tests +### +# +### Rights on mysql.proc +# +create user user@localhost; +grant all privileges on mysql.* to user@localhost; +grant all privileges on test.* to user@localhost; +connect conn1, localhost, user, , test; +show procedure code test_db.sp; +Pos Instruction +0 stmt 0 "select 1" +show function code test_db.fn; +Pos Instruction +0 freturn int 1 +show package body code test_db.pk; +Pos Instruction +0 set pkv@0 1 +1 set pkv@0 2 +connection default; +disconnect conn1; +revoke all privileges on mysql.* from user@localhost; +# +### No privileges +# +connect conn1, localhost, user, , test; +show procedure code test_db.sp; +ERROR 42000: PROCEDURE sp does not exist +show function code test_db.fn; +ERROR 42000: FUNCTION fn does not exist +show package body code test_db.pk; +ERROR 42000: PACKAGE BODY pk does not exist +connection default; +disconnect conn1; +# +### Execute provilege PROCEDURE/FUNCTION +# +grant execute on procedure test_db.sp to user@localhost; +grant execute on function test_db.fn to user@localhost; +connect conn1, localhost, user, , test; +show procedure code test_db.sp; +ERROR 42000: PROCEDURE sp does not exist +show function code test_db.fn; +ERROR 42000: FUNCTION fn does not exist +connection default; +disconnect conn1; +revoke execute on procedure test_db.sp from user@localhost; +revoke execute on function test_db.fn from user@localhost; +# +### Execute provilege PACKAGE+ PACKAGE BODY- +# +SET sql_mode=ORACLE; +grant execute on package test_db.pk to user@localhost; +SET sql_mode=@save_sql_mode; +connect conn1, localhost, user, , test; +show package body code test_db.pk; +ERROR 42000: PACKAGE BODY pk does not exist +connection default; +disconnect conn1; +SET sql_mode=ORACLE; +revoke execute on package test_db.pk from user@localhost; +SET sql_mode=@save_sql_mode; +# +### Execute provilege PACKAGE- PACKAGE BODY+ +# +SET sql_mode=ORACLE; +grant execute on package body test_db.pk to user@localhost; +SET sql_mode=@save_sql_mode; +connect conn1, localhost, user, , test; +show package body code test_db.pk; +ERROR 42000: PACKAGE BODY pk does not exist +connection default; +disconnect conn1; +SET sql_mode=ORACLE; +revoke execute on package body test_db.pk from user@localhost; +SET sql_mode=@save_sql_mode; +# +### Alter routine provilege PROCEDURE/FUNCTION +# +grant alter routine on procedure test_db.sp to user@localhost; +grant alter routine on function test_db.fn to user@localhost; +connect conn1, localhost, user, , test; +show procedure code test_db.sp; +ERROR 42000: PROCEDURE sp does not exist +show function code test_db.fn; +ERROR 42000: FUNCTION fn does not exist +connection default; +disconnect conn1; +revoke alter routine on procedure test_db.sp from user@localhost; +revoke alter routine on function test_db.fn from user@localhost; +# +### Alter routine provilege PACKAGE+ PACKAGE BODY- +# +SET sql_mode=ORACLE; +grant alter routine on package test_db.pk to user@localhost; +SET sql_mode=@save_sql_mode; +connect conn1, localhost, user, , test; +show package body code test_db.pk; +ERROR 42000: PACKAGE BODY pk does not exist +connection default; +disconnect conn1; +SET sql_mode=ORACLE; +revoke alter routine on package test_db.pk from user@localhost; +SET sql_mode=@save_sql_mode; +# +### Alter routine provilege PACKAGE+ PACKAGE BODY- +# +SET sql_mode=ORACLE; +grant alter routine on package body test_db.pk to user@localhost; +SET sql_mode=@save_sql_mode; +connect conn1, localhost, user, , test; +show package body code test_db.pk; +ERROR 42000: PACKAGE BODY pk does not exist +connection default; +disconnect conn1; +SET sql_mode=ORACLE; +revoke alter routine on package body test_db.pk from user@localhost; +SET sql_mode=@save_sql_mode; +### +### SHOW CREATE PROCEDURE tests +### +# +### Global "show create routine" test +# +grant show create routine on *.* to user@localhost; +show grants for user@localhost; +Grants for user@localhost +GRANT SHOW CREATE ROUTINE ON *.* TO `user`@`localhost` +GRANT ALL PRIVILEGES ON `test`.* TO `user`@`localhost` +connect conn1, localhost, user, , test; +show procedure code test_db.sp; +Pos Instruction +0 stmt 0 "select 1" +show function code test_db.fn; +Pos Instruction +0 freturn int 1 +show package body code test_db.pk; +Pos Instruction +0 set pkv@0 1 +1 set pkv@0 2 +connection default; +disconnect conn1; +revoke show create routine on *.* from user@localhost; +# +### DB-level "show create routine" but other DB test +# +grant show create routine on db_test.* to user@localhost; +show grants for user@localhost; +Grants for user@localhost +GRANT USAGE ON *.* TO `user`@`localhost` +GRANT ALL PRIVILEGES ON `test`.* TO `user`@`localhost` +GRANT SHOW CREATE ROUTINE ON `db_test`.* TO `user`@`localhost` +connect conn1, localhost, user, , test; +show procedure code test_db.sp; +ERROR 42000: PROCEDURE sp does not exist +show function code test_db.fn; +ERROR 42000: FUNCTION fn does not exist +show package body code test_db.pk; +ERROR 42000: PACKAGE BODY pk does not exist +connection default; +disconnect conn1; +revoke show create routine on db_test.* from user@localhost; +# +### DB-level "show create routine" test +# +grant show create routine on test_db.* to user@localhost; +show grants for user@localhost; +Grants for user@localhost +GRANT USAGE ON *.* TO `user`@`localhost` +GRANT ALL PRIVILEGES ON `test`.* TO `user`@`localhost` +GRANT SHOW CREATE ROUTINE ON `test_db`.* TO `user`@`localhost` +connect conn1, localhost, user, , test; +show procedure code test_db.sp; +Pos Instruction +0 stmt 0 "select 1" +show function code test_db.fn; +Pos Instruction +0 freturn int 1 +show package body code test_db.pk; +Pos Instruction +0 set pkv@0 1 +1 set pkv@0 2 +connection default; +disconnect conn1; +revoke show create routine on test_db.* from user@localhost; +# +### Routine-level "show create routine" PROCEDURE and FUNCTION +# +grant show create routine on procedure test_db.sp to user@localhost; +grant show create routine on function test_db.fn to user@localhost; +connect conn1, localhost, user, , test; +show procedure code test_db.sp; +Pos Instruction +0 stmt 0 "select 1" +show function code test_db.fn; +Pos Instruction +0 freturn int 1 +connection default; +disconnect conn1; +revoke show create routine on procedure test_db.sp from user@localhost; +revoke show create routine on function test_db.fn from user@localhost; +# +### Routine-level "show create routine" PACKAGE+ PACKAGE BODY- +# +SET sql_mode=ORACLE; +grant show create routine on package test_db.pk to user@localhost; +SET sql_mode=@save_sql_mode; +connect conn1, localhost, user, , test; +show package body code test_db.pk; +ERROR 42000: PACKAGE BODY pk does not exist +connection default; +disconnect conn1; +SET sql_mode=ORACLE; +revoke show create routine on package test_db.pk from user@localhost; +SET sql_mode=@save_sql_mode; +# +### Routine-level "show create routine" PACKAGE- PACKAGE BODY+ +# +SET sql_mode=ORACLE; +grant show create routine on package body test_db.pk to user@localhost; +SET sql_mode=@save_sql_mode; +connect conn1, localhost, user, , test; +show package body code test_db.pk; +Pos Instruction +0 set pkv@0 1 +1 set pkv@0 2 +connection default; +disconnect conn1; +SET sql_mode=ORACLE; +revoke show create routine on package body test_db.pk from user@localhost; +SET sql_mode=@save_sql_mode; +drop database test_db; +drop user user@localhost; +# +# End of 11.3 tests +# diff --git a/mysql-test/main/sp-security-debug.test b/mysql-test/main/sp-security-debug.test new file mode 100644 index 00000000000..58d37a67f74 --- /dev/null +++ b/mysql-test/main/sp-security-debug.test @@ -0,0 +1,368 @@ +# +# Testing SQL SECURITY of stored procedures (DEBUGG binaries) +# + +--source include/have_debug.inc +# Can't test with embedded server that doesn't support grants +--source include/not_embedded.inc +--source include/default_charset.inc +set @@global.character_set_server=@@session.character_set_server; + + +--echo # +--echo # MDEV-29167: new db-level SHOW CREATE ROUTINE privilege +--echo # + +--echo ### +--echo ### SHOW-Like commad test +--echo ### + +SET @save_sql_mode=@@sql_mode; + +--echo # +--echo ### Prepare functions for the test and SHOW-like by owner +--echo # + +create database test_db; +use test_db; +create procedure test_db.sp() select 1; +show procedure code test_db.sp; +CREATE FUNCTION test_db.fn() RETURNS INT RETURN 1; +show function code test_db.fn; + +SET sql_mode=ORACLE; +DELIMITER $$; +CREATE PACKAGE test_db.pk AS + FUNCTION pkf() RETURN INT; + PROCEDURE pkp(); +END; +$$ +CREATE PACKAGE BODY test_db.pk AS + pkv INT:=1; + + PROCEDURE pkhp() AS + BEGIN + SELECT pkv FROM DUAL; + END; + + FUNCTION pkhf() RETURN INT AS + BEGIN + RETURN pkv; + END; + + PROCEDURE pkp() AS + BEGIN + CALL pkhp(); + END; + FUNCTION pkf() RETURN INT AS + BEGIN + RETURN pkhf(); + END; + +BEGIN + pkv:=2; +END; +$$ +DELIMITER ;$$ + +SET sql_mode=@save_sql_mode; +--error ER_PARSE_ERROR +show package code test_db.pk; +show package body code test_db.pk; + +use test; + + +--echo ### +--echo ### Pre-"SHOW-CREATE-ROUTINE" behaviour tests +--echo ### + + +--echo # +--echo ### Rights on mysql.proc +--echo # + +create user user@localhost; +grant all privileges on mysql.* to user@localhost; +grant all privileges on test.* to user@localhost; + +connect conn1, localhost, user, , test; + +show procedure code test_db.sp; +show function code test_db.fn; +show package body code test_db.pk; + +connection default; +disconnect conn1; + +revoke all privileges on mysql.* from user@localhost; + + +--echo # +--echo ### No privileges +--echo # + +connect conn1, localhost, user, , test; + +--error ER_SP_DOES_NOT_EXIST +show procedure code test_db.sp; +--error ER_SP_DOES_NOT_EXIST +show function code test_db.fn; +--error ER_SP_DOES_NOT_EXIST +show package body code test_db.pk; + +connection default; +disconnect conn1; + +--echo # +--echo ### Execute provilege PROCEDURE/FUNCTION +--echo # + +grant execute on procedure test_db.sp to user@localhost; +grant execute on function test_db.fn to user@localhost; + +connect conn1, localhost, user, , test; + +--error ER_SP_DOES_NOT_EXIST +show procedure code test_db.sp; +--error ER_SP_DOES_NOT_EXIST +show function code test_db.fn; + +connection default; +disconnect conn1; + +revoke execute on procedure test_db.sp from user@localhost; +revoke execute on function test_db.fn from user@localhost; + +--echo # +--echo ### Execute provilege PACKAGE+ PACKAGE BODY- +--echo # + +SET sql_mode=ORACLE; +grant execute on package test_db.pk to user@localhost; +SET sql_mode=@save_sql_mode; + +connect conn1, localhost, user, , test; + +--error ER_SP_DOES_NOT_EXIST +show package body code test_db.pk; + +connection default; +disconnect conn1; + +SET sql_mode=ORACLE; +revoke execute on package test_db.pk from user@localhost; +SET sql_mode=@save_sql_mode; + + +--echo # +--echo ### Execute provilege PACKAGE- PACKAGE BODY+ +--echo # + +SET sql_mode=ORACLE; +grant execute on package body test_db.pk to user@localhost; +SET sql_mode=@save_sql_mode; + +connect conn1, localhost, user, , test; + +--error ER_SP_DOES_NOT_EXIST +show package body code test_db.pk; + +connection default; +disconnect conn1; + +SET sql_mode=ORACLE; +revoke execute on package body test_db.pk from user@localhost; +SET sql_mode=@save_sql_mode; + +--echo # +--echo ### Alter routine provilege PROCEDURE/FUNCTION +--echo # + +grant alter routine on procedure test_db.sp to user@localhost; +grant alter routine on function test_db.fn to user@localhost; + +connect conn1, localhost, user, , test; + +--error ER_SP_DOES_NOT_EXIST +show procedure code test_db.sp; +--error ER_SP_DOES_NOT_EXIST +show function code test_db.fn; + +connection default; +disconnect conn1; + + +revoke alter routine on procedure test_db.sp from user@localhost; +revoke alter routine on function test_db.fn from user@localhost; + +--echo # +--echo ### Alter routine provilege PACKAGE+ PACKAGE BODY- +--echo # + +SET sql_mode=ORACLE; +grant alter routine on package test_db.pk to user@localhost; +SET sql_mode=@save_sql_mode; + +connect conn1, localhost, user, , test; + +--error ER_SP_DOES_NOT_EXIST +show package body code test_db.pk; + +connection default; +disconnect conn1; + +SET sql_mode=ORACLE; +revoke alter routine on package test_db.pk from user@localhost; +SET sql_mode=@save_sql_mode; + + +--echo # +--echo ### Alter routine provilege PACKAGE+ PACKAGE BODY- +--echo # + +SET sql_mode=ORACLE; +grant alter routine on package body test_db.pk to user@localhost; +SET sql_mode=@save_sql_mode; + +connect conn1, localhost, user, , test; + +--error ER_SP_DOES_NOT_EXIST +show package body code test_db.pk; +connection default; +disconnect conn1; + +SET sql_mode=ORACLE; +revoke alter routine on package body test_db.pk from user@localhost; +SET sql_mode=@save_sql_mode; + + +--echo ### +--echo ### SHOW CREATE PROCEDURE tests +--echo ### + + +--echo # +--echo ### Global "show create routine" test +--echo # + +grant show create routine on *.* to user@localhost; +show grants for user@localhost; + +connect conn1, localhost, user, , test; + +show procedure code test_db.sp; +show function code test_db.fn; +show package body code test_db.pk; + +connection default; +disconnect conn1; + +revoke show create routine on *.* from user@localhost; + +--echo # +--echo ### DB-level "show create routine" but other DB test +--echo # + +grant show create routine on db_test.* to user@localhost; +show grants for user@localhost; + +connect conn1, localhost, user, , test; + +--error ER_SP_DOES_NOT_EXIST +show procedure code test_db.sp; +--error ER_SP_DOES_NOT_EXIST +show function code test_db.fn; +--error ER_SP_DOES_NOT_EXIST +show package body code test_db.pk; + +connection default; +disconnect conn1; + +revoke show create routine on db_test.* from user@localhost; + +--echo # +--echo ### DB-level "show create routine" test +--echo # + +grant show create routine on test_db.* to user@localhost; +show grants for user@localhost; + +connect conn1, localhost, user, , test; + +show procedure code test_db.sp; +show function code test_db.fn; +show package body code test_db.pk; + +connection default; +disconnect conn1; + +revoke show create routine on test_db.* from user@localhost; + + +--echo # +--echo ### Routine-level "show create routine" PROCEDURE and FUNCTION +--echo # + +grant show create routine on procedure test_db.sp to user@localhost; +grant show create routine on function test_db.fn to user@localhost; + +connect conn1, localhost, user, , test; + +show procedure code test_db.sp; +show function code test_db.fn; + +connection default; +disconnect conn1; + +revoke show create routine on procedure test_db.sp from user@localhost; +revoke show create routine on function test_db.fn from user@localhost; + + +--echo # +--echo ### Routine-level "show create routine" PACKAGE+ PACKAGE BODY- +--echo # + +SET sql_mode=ORACLE; +grant show create routine on package test_db.pk to user@localhost; +SET sql_mode=@save_sql_mode; + +connect conn1, localhost, user, , test; + +--error ER_SP_DOES_NOT_EXIST +show package body code test_db.pk; + +connection default; +disconnect conn1; + +SET sql_mode=ORACLE; +revoke show create routine on package test_db.pk from user@localhost; +SET sql_mode=@save_sql_mode; + + +--echo # +--echo ### Routine-level "show create routine" PACKAGE- PACKAGE BODY+ +--echo # + +SET sql_mode=ORACLE; +grant show create routine on package body test_db.pk to user@localhost; +SET sql_mode=@save_sql_mode; + + +connect conn1, localhost, user, , test; + +show package body code test_db.pk; + +connection default; +disconnect conn1; + +SET sql_mode=ORACLE; +revoke show create routine on package body test_db.pk from user@localhost; +SET sql_mode=@save_sql_mode; + +drop database test_db; +drop user user@localhost; + +--echo # +--echo # End of 11.3 tests +--echo # diff --git a/mysql-test/main/sp-security.result b/mysql-test/main/sp-security.result index f25bff8a920..93e05c522c0 100644 --- a/mysql-test/main/sp-security.result +++ b/mysql-test/main/sp-security.result @@ -240,7 +240,7 @@ grant all privileges on procedure sptest.p1 to userc@localhost; show grants for userc@localhost; Grants for userc@localhost GRANT USAGE ON *.* TO `userc`@`localhost` -GRANT EXECUTE, ALTER ROUTINE ON PROCEDURE `sptest`.`p1` TO `userc`@`localhost` WITH GRANT OPTION +GRANT EXECUTE, ALTER ROUTINE, SHOW CREATE ROUTINE ON PROCEDURE `sptest`.`p1` TO `userc`@`localhost` WITH GRANT OPTION show grants for userb@localhost; Grants for userb@localhost GRANT USAGE ON *.* TO `userb`@`localhost` @@ -843,3 +843,890 @@ drop function f; # # End of 10.6 tests # +# +# MDEV-29167: new db-level SHOW CREATE ROUTINE privilege +# +### +### SHOW-Like commad test +### +SET @save_sql_mode=@@sql_mode; +# +### Prepare functions for the test and SHOW-like by root +# +create database test_db; +use test_db; +create procedure test_db.sp() select 1; +show create procedure test_db.sp; +Procedure sql_mode Create Procedure character_set_client collation_connection Database Collation +sp STRICT_TRANS_TABLES,ERROR_FOR_DIVISION_BY_ZERO,NO_AUTO_CREATE_USER,NO_ENGINE_SUBSTITUTION CREATE DEFINER=`root`@`localhost` PROCEDURE `sp`() +select 1 latin1 latin1_swedish_ci latin1_swedish_ci +SHOW PROCEDURE STATUS WHERE name="sp"; +Db Name Type Definer Modified Created Security_type Comment character_set_client collation_connection Database Collation +test_db sp PROCEDURE root@localhost # # DEFINER latin1 latin1_swedish_ci latin1_swedish_ci +SELECT ROUTINE_NAME, ROUTINE_DEFINITION from information_schema.ROUTINES where ROUTINE_NAME="sp"; +ROUTINE_NAME ROUTINE_DEFINITION +sp select 1 +CREATE FUNCTION test_db.fn() RETURNS INT RETURN 1; +show create function test_db.fn; +Function sql_mode Create Function character_set_client collation_connection Database Collation +fn STRICT_TRANS_TABLES,ERROR_FOR_DIVISION_BY_ZERO,NO_AUTO_CREATE_USER,NO_ENGINE_SUBSTITUTION CREATE DEFINER=`root`@`localhost` FUNCTION `fn`() RETURNS int(11) +RETURN 1 latin1 latin1_swedish_ci latin1_swedish_ci +SHOW FUNCTION STATUS WHERE name="fn"; +Db Name Type Definer Modified Created Security_type Comment character_set_client collation_connection Database Collation +test_db fn FUNCTION root@localhost # # DEFINER latin1 latin1_swedish_ci latin1_swedish_ci +SELECT ROUTINE_NAME, ROUTINE_DEFINITION from information_schema.ROUTINES where ROUTINE_NAME="fn"; +ROUTINE_NAME ROUTINE_DEFINITION +fn RETURN 1 +SET sql_mode=ORACLE; +CREATE PACKAGE test_db.pk AS +FUNCTION pkf() RETURN INT; +PROCEDURE pkp(); +END; +$$ +CREATE PACKAGE BODY test_db.pk AS +pkv INT:=1; +PROCEDURE pkhp() AS +BEGIN +SELECT pkv FROM DUAL; +END; +FUNCTION pkhf() RETURN INT AS +BEGIN +RETURN pkv; +END; +PROCEDURE pkp() AS +BEGIN +CALL pkhp(); +END; +FUNCTION pkf() RETURN INT AS +BEGIN +RETURN pkhf(); +END; +BEGIN +pkv:=2; +END; +$$ +SET sql_mode=@save_sql_mode; +show create package test_db.pk; +Package sql_mode Create Package character_set_client collation_connection Database Collation +pk PIPES_AS_CONCAT,ANSI_QUOTES,IGNORE_SPACE,ORACLE,NO_KEY_OPTIONS,NO_TABLE_OPTIONS,NO_FIELD_OPTIONS,NO_AUTO_CREATE_USER,SIMULTANEOUS_ASSIGNMENT CREATE DEFINER="root"@"localhost" PACKAGE "pk" AS +FUNCTION pkf() RETURN INT; +PROCEDURE pkp(); +END latin1 latin1_swedish_ci latin1_swedish_ci +show create package body test_db.pk; +Package body sql_mode Create Package Body character_set_client collation_connection Database Collation +pk PIPES_AS_CONCAT,ANSI_QUOTES,IGNORE_SPACE,ORACLE,NO_KEY_OPTIONS,NO_TABLE_OPTIONS,NO_FIELD_OPTIONS,NO_AUTO_CREATE_USER,SIMULTANEOUS_ASSIGNMENT CREATE DEFINER="root"@"localhost" PACKAGE BODY "pk" AS +pkv INT:=1; +PROCEDURE pkhp() AS +BEGIN +SELECT pkv FROM DUAL; +END; +FUNCTION pkhf() RETURN INT AS +BEGIN +RETURN pkv; +END; +PROCEDURE pkp() AS +BEGIN +CALL pkhp(); +END; +FUNCTION pkf() RETURN INT AS +BEGIN +RETURN pkhf(); +END; +BEGIN +pkv:=2; +END latin1 latin1_swedish_ci latin1_swedish_ci +SHOW PACKAGE STATUS WHERE name="pk"; +Db Name Type Definer Modified Created Security_type Comment character_set_client collation_connection Database Collation +test_db pk PACKAGE root@localhost # # DEFINER latin1 latin1_swedish_ci latin1_swedish_ci +SELECT ROUTINE_NAME, ROUTINE_TYPE, ROUTINE_DEFINITION from information_schema.ROUTINES where ROUTINE_NAME="pk"; +ROUTINE_NAME ROUTINE_TYPE ROUTINE_DEFINITION +pk PACKAGE AS +FUNCTION pkf() RETURN INT; +PROCEDURE pkp(); +END +pk PACKAGE BODY AS +pkv INT:=1; +PROCEDURE pkhp() AS +BEGIN +SELECT pkv FROM DUAL; +END; +FUNCTION pkhf() RETURN INT AS +BEGIN +RETURN pkv; +END; +PROCEDURE pkp() AS +BEGIN +CALL pkhp(); +END; +FUNCTION pkf() RETURN INT AS +BEGIN +RETURN pkhf(); +END; +BEGIN +pkv:=2; +END +use test; +### +### Pre-"SHOW-CREATE-ROUTINE" behaviour tests +### +# +### Rights on mysql.proc +# +create user user@localhost; +grant all privileges on mysql.* to user@localhost; +grant all privileges on test.* to user@localhost; +connect conn1, localhost, user, , test; +show create procedure test_db.sp; +Procedure sql_mode Create Procedure character_set_client collation_connection Database Collation +sp STRICT_TRANS_TABLES,ERROR_FOR_DIVISION_BY_ZERO,NO_AUTO_CREATE_USER,NO_ENGINE_SUBSTITUTION CREATE DEFINER=`root`@`localhost` PROCEDURE `sp`() +select 1 latin1 latin1_swedish_ci latin1_swedish_ci +SHOW PROCEDURE STATUS WHERE name="sp"; +Db Name Type Definer Modified Created Security_type Comment character_set_client collation_connection Database Collation +test_db sp PROCEDURE root@localhost # # DEFINER latin1 latin1_swedish_ci latin1_swedish_ci +SELECT ROUTINE_NAME from information_schema.ROUTINES where ROUTINE_NAME="sp"; +ROUTINE_NAME +sp +show create function test_db.fn; +Function sql_mode Create Function character_set_client collation_connection Database Collation +fn STRICT_TRANS_TABLES,ERROR_FOR_DIVISION_BY_ZERO,NO_AUTO_CREATE_USER,NO_ENGINE_SUBSTITUTION CREATE DEFINER=`root`@`localhost` FUNCTION `fn`() RETURNS int(11) +RETURN 1 latin1 latin1_swedish_ci latin1_swedish_ci +SHOW FUNCTION STATUS WHERE name="fn"; +Db Name Type Definer Modified Created Security_type Comment character_set_client collation_connection Database Collation +test_db fn FUNCTION root@localhost # # DEFINER latin1 latin1_swedish_ci latin1_swedish_ci +SELECT ROUTINE_NAME, ROUTINE_DEFINITION from information_schema.ROUTINES where +ROUTINE_NAME="fn"; +ROUTINE_NAME ROUTINE_DEFINITION +fn RETURN 1 +show create package test_db.pk; +Package sql_mode Create Package character_set_client collation_connection Database Collation +pk PIPES_AS_CONCAT,ANSI_QUOTES,IGNORE_SPACE,ORACLE,NO_KEY_OPTIONS,NO_TABLE_OPTIONS,NO_FIELD_OPTIONS,NO_AUTO_CREATE_USER,SIMULTANEOUS_ASSIGNMENT CREATE DEFINER="root"@"localhost" PACKAGE "pk" AS +FUNCTION pkf() RETURN INT; +PROCEDURE pkp(); +END latin1 latin1_swedish_ci latin1_swedish_ci +show create package body test_db.pk; +Package body sql_mode Create Package Body character_set_client collation_connection Database Collation +pk PIPES_AS_CONCAT,ANSI_QUOTES,IGNORE_SPACE,ORACLE,NO_KEY_OPTIONS,NO_TABLE_OPTIONS,NO_FIELD_OPTIONS,NO_AUTO_CREATE_USER,SIMULTANEOUS_ASSIGNMENT CREATE DEFINER="root"@"localhost" PACKAGE BODY "pk" AS +pkv INT:=1; +PROCEDURE pkhp() AS +BEGIN +SELECT pkv FROM DUAL; +END; +FUNCTION pkhf() RETURN INT AS +BEGIN +RETURN pkv; +END; +PROCEDURE pkp() AS +BEGIN +CALL pkhp(); +END; +FUNCTION pkf() RETURN INT AS +BEGIN +RETURN pkhf(); +END; +BEGIN +pkv:=2; +END latin1 latin1_swedish_ci latin1_swedish_ci +SHOW PACKAGE STATUS WHERE name="pk"; +Db Name Type Definer Modified Created Security_type Comment character_set_client collation_connection Database Collation +test_db pk PACKAGE root@localhost # # DEFINER latin1 latin1_swedish_ci latin1_swedish_ci +SELECT ROUTINE_NAME, ROUTINE_TYPE, ROUTINE_DEFINITION from information_schema.ROUTINES where ROUTINE_NAME="pk"; +ROUTINE_NAME ROUTINE_TYPE ROUTINE_DEFINITION +pk PACKAGE AS +FUNCTION pkf() RETURN INT; +PROCEDURE pkp(); +END +pk PACKAGE BODY AS +pkv INT:=1; +PROCEDURE pkhp() AS +BEGIN +SELECT pkv FROM DUAL; +END; +FUNCTION pkhf() RETURN INT AS +BEGIN +RETURN pkv; +END; +PROCEDURE pkp() AS +BEGIN +CALL pkhp(); +END; +FUNCTION pkf() RETURN INT AS +BEGIN +RETURN pkhf(); +END; +BEGIN +pkv:=2; +END +connection default; +disconnect conn1; +revoke all privileges on mysql.* from user@localhost; +# +### No privileges +# +connect conn1, localhost, user, , test; +show create procedure test_db.sp; +ERROR 42000: PROCEDURE sp does not exist +SHOW PROCEDURE STATUS WHERE name="sp"; +Db Name Type Definer Modified Created Security_type Comment character_set_client collation_connection Database Collation +SELECT ROUTINE_NAME from information_schema.ROUTINES where ROUTINE_NAME="sp"; +ROUTINE_NAME +show create function test_db.fn; +ERROR 42000: FUNCTION fn does not exist +SHOW FUNCTION STATUS WHERE name="fn"; +Db Name Type Definer Modified Created Security_type Comment character_set_client collation_connection Database Collation +SELECT ROUTINE_NAME, ROUTINE_DEFINITION from information_schema.ROUTINES where +ROUTINE_NAME="fn"; +ROUTINE_NAME ROUTINE_DEFINITION +show create package test_db.pk; +ERROR 42000: PACKAGE pk does not exist +show create package body test_db.pk; +ERROR 42000: PACKAGE BODY pk does not exist +SHOW PACKAGE STATUS WHERE name="pk"; +Db Name Type Definer Modified Created Security_type Comment character_set_client collation_connection Database Collation +SELECT ROUTINE_NAME, ROUTINE_TYPE, ROUTINE_DEFINITION from information_schema.ROUTINES where ROUTINE_NAME="pk"; +ROUTINE_NAME ROUTINE_TYPE ROUTINE_DEFINITION +connection default; +disconnect conn1; +# +### Execute provilege PROCEDURE/FUNCTION +# +grant execute on procedure test_db.sp to user@localhost; +grant execute on function test_db.fn to user@localhost; +connect conn1, localhost, user, , test; +show create procedure test_db.sp; +Procedure sql_mode Create Procedure character_set_client collation_connection Database Collation +sp STRICT_TRANS_TABLES,ERROR_FOR_DIVISION_BY_ZERO,NO_AUTO_CREATE_USER,NO_ENGINE_SUBSTITUTION NULL latin1 latin1_swedish_ci latin1_swedish_ci +SHOW PROCEDURE STATUS WHERE name="sp"; +Db Name Type Definer Modified Created Security_type Comment character_set_client collation_connection Database Collation +test_db sp PROCEDURE root@localhost # # DEFINER latin1 latin1_swedish_ci latin1_swedish_ci +SELECT ROUTINE_NAME from information_schema.ROUTINES where ROUTINE_NAME="sp"; +ROUTINE_NAME +sp +call test_db.sp(); +1 +1 +show create function test_db.fn; +Function sql_mode Create Function character_set_client collation_connection Database Collation +fn STRICT_TRANS_TABLES,ERROR_FOR_DIVISION_BY_ZERO,NO_AUTO_CREATE_USER,NO_ENGINE_SUBSTITUTION NULL latin1 latin1_swedish_ci latin1_swedish_ci +SHOW FUNCTION STATUS WHERE name="fn"; +Db Name Type Definer Modified Created Security_type Comment character_set_client collation_connection Database Collation +test_db fn FUNCTION root@localhost # # DEFINER latin1 latin1_swedish_ci latin1_swedish_ci +SELECT ROUTINE_NAME, ROUTINE_DEFINITION from information_schema.ROUTINES where +ROUTINE_NAME="fn"; +ROUTINE_NAME ROUTINE_DEFINITION +fn NULL +select test_db.fn(); +test_db.fn() +1 +connection default; +disconnect conn1; +revoke execute on procedure test_db.sp from user@localhost; +revoke execute on function test_db.fn from user@localhost; +# +### Execute provilege PACKAGE+ PACKAGE BODY- +# +SET sql_mode=ORACLE; +grant execute on package test_db.pk to user@localhost; +SET sql_mode=@save_sql_mode; +connect conn1, localhost, user, , test; +show create package test_db.pk; +Package sql_mode Create Package character_set_client collation_connection Database Collation +pk PIPES_AS_CONCAT,ANSI_QUOTES,IGNORE_SPACE,ORACLE,NO_KEY_OPTIONS,NO_TABLE_OPTIONS,NO_FIELD_OPTIONS,NO_AUTO_CREATE_USER,SIMULTANEOUS_ASSIGNMENT NULL latin1 latin1_swedish_ci latin1_swedish_ci +show create package body test_db.pk; +ERROR 42000: PACKAGE BODY pk does not exist +SHOW PACKAGE STATUS WHERE name="pk"; +Db Name Type Definer Modified Created Security_type Comment character_set_client collation_connection Database Collation +test_db pk PACKAGE root@localhost # # DEFINER latin1 latin1_swedish_ci latin1_swedish_ci +SELECT ROUTINE_NAME, ROUTINE_TYPE, ROUTINE_DEFINITION from information_schema.ROUTINES where ROUTINE_NAME="pk"; +ROUTINE_NAME ROUTINE_TYPE ROUTINE_DEFINITION +pk PACKAGE NULL +call test_db.pk.pkp(); +ERROR 42000: execute command denied to user 'user'@'localhost' for routine 'test_db.pk' +select test_db.pk.pkf(); +ERROR 42000: execute command denied to user 'user'@'localhost' for routine 'test_db.pk' +connection default; +disconnect conn1; +SET sql_mode=ORACLE; +revoke execute on package test_db.pk from user@localhost; +SET sql_mode=@save_sql_mode; +# +### Execute provilege PACKAGE- PACKAGE BODY+ +# +SET sql_mode=ORACLE; +grant execute on package body test_db.pk to user@localhost; +SET sql_mode=@save_sql_mode; +connect conn1, localhost, user, , test; +show create package test_db.pk; +ERROR 42000: PACKAGE pk does not exist +show create package body test_db.pk; +Package body sql_mode Create Package Body character_set_client collation_connection Database Collation +pk PIPES_AS_CONCAT,ANSI_QUOTES,IGNORE_SPACE,ORACLE,NO_KEY_OPTIONS,NO_TABLE_OPTIONS,NO_FIELD_OPTIONS,NO_AUTO_CREATE_USER,SIMULTANEOUS_ASSIGNMENT NULL latin1 latin1_swedish_ci latin1_swedish_ci +SHOW PACKAGE STATUS WHERE name="pk"; +Db Name Type Definer Modified Created Security_type Comment character_set_client collation_connection Database Collation +SELECT ROUTINE_NAME, ROUTINE_TYPE, ROUTINE_DEFINITION from information_schema.ROUTINES where ROUTINE_NAME="pk"; +ROUTINE_NAME ROUTINE_TYPE ROUTINE_DEFINITION +pk PACKAGE BODY NULL +call test_db.pk.pkp(); +pkv +2 +select test_db.pk.pkf(); +test_db.pk.pkf() +2 +connection default; +disconnect conn1; +SET sql_mode=ORACLE; +revoke execute on package body test_db.pk from user@localhost; +SET sql_mode=@save_sql_mode; +# +### Alter routine provilege PROCEDURE/FUNCTION +# +grant alter routine on procedure test_db.sp to user@localhost; +grant alter routine on function test_db.fn to user@localhost; +connect conn1, localhost, user, , test; +show create procedure test_db.sp; +Procedure sql_mode Create Procedure character_set_client collation_connection Database Collation +sp STRICT_TRANS_TABLES,ERROR_FOR_DIVISION_BY_ZERO,NO_AUTO_CREATE_USER,NO_ENGINE_SUBSTITUTION NULL latin1 latin1_swedish_ci latin1_swedish_ci +SHOW PROCEDURE STATUS WHERE name="sp"; +Db Name Type Definer Modified Created Security_type Comment character_set_client collation_connection Database Collation +test_db sp PROCEDURE root@localhost # # DEFINER latin1 latin1_swedish_ci latin1_swedish_ci +SELECT ROUTINE_NAME from information_schema.ROUTINES where ROUTINE_NAME="sp"; +ROUTINE_NAME +sp +show create function test_db.fn; +Function sql_mode Create Function character_set_client collation_connection Database Collation +fn STRICT_TRANS_TABLES,ERROR_FOR_DIVISION_BY_ZERO,NO_AUTO_CREATE_USER,NO_ENGINE_SUBSTITUTION NULL latin1 latin1_swedish_ci latin1_swedish_ci +SHOW FUNCTION STATUS WHERE name="fn"; +Db Name Type Definer Modified Created Security_type Comment character_set_client collation_connection Database Collation +test_db fn FUNCTION root@localhost # # DEFINER latin1 latin1_swedish_ci latin1_swedish_ci +SELECT ROUTINE_NAME, ROUTINE_DEFINITION from information_schema.ROUTINES where +ROUTINE_NAME="fn"; +ROUTINE_NAME ROUTINE_DEFINITION +fn NULL +connection default; +disconnect conn1; +revoke alter routine on procedure test_db.sp from user@localhost; +revoke alter routine on function test_db.fn from user@localhost; +# +### Alter routine provilege PACKAGE+ PACKAGE BODY- +# +SET sql_mode=ORACLE; +grant alter routine on package test_db.pk to user@localhost; +SET sql_mode=@save_sql_mode; +connect conn1, localhost, user, , test; +show create package test_db.pk; +Package sql_mode Create Package character_set_client collation_connection Database Collation +pk PIPES_AS_CONCAT,ANSI_QUOTES,IGNORE_SPACE,ORACLE,NO_KEY_OPTIONS,NO_TABLE_OPTIONS,NO_FIELD_OPTIONS,NO_AUTO_CREATE_USER,SIMULTANEOUS_ASSIGNMENT NULL latin1 latin1_swedish_ci latin1_swedish_ci +show create package body test_db.pk; +ERROR 42000: PACKAGE BODY pk does not exist +SHOW PACKAGE STATUS WHERE name="pk"; +Db Name Type Definer Modified Created Security_type Comment character_set_client collation_connection Database Collation +test_db pk PACKAGE root@localhost # # DEFINER latin1 latin1_swedish_ci latin1_swedish_ci +SELECT ROUTINE_NAME, ROUTINE_TYPE, ROUTINE_DEFINITION from information_schema.ROUTINES where ROUTINE_NAME="pk"; +ROUTINE_NAME ROUTINE_TYPE ROUTINE_DEFINITION +pk PACKAGE NULL +connection default; +disconnect conn1; +SET sql_mode=ORACLE; +revoke alter routine on package test_db.pk from user@localhost; +SET sql_mode=@save_sql_mode; +# +### Alter routine provilege PACKAGE+ PACKAGE BODY- +# +SET sql_mode=ORACLE; +grant alter routine on package body test_db.pk to user@localhost; +SET sql_mode=@save_sql_mode; +connect conn1, localhost, user, , test; +show create package test_db.pk; +ERROR 42000: PACKAGE pk does not exist +show create package body test_db.pk; +Package body sql_mode Create Package Body character_set_client collation_connection Database Collation +pk PIPES_AS_CONCAT,ANSI_QUOTES,IGNORE_SPACE,ORACLE,NO_KEY_OPTIONS,NO_TABLE_OPTIONS,NO_FIELD_OPTIONS,NO_AUTO_CREATE_USER,SIMULTANEOUS_ASSIGNMENT NULL latin1 latin1_swedish_ci latin1_swedish_ci +SHOW PACKAGE STATUS WHERE name="pk"; +Db Name Type Definer Modified Created Security_type Comment character_set_client collation_connection Database Collation +SELECT ROUTINE_NAME, ROUTINE_TYPE, ROUTINE_DEFINITION from information_schema.ROUTINES where ROUTINE_NAME="pk"; +ROUTINE_NAME ROUTINE_TYPE ROUTINE_DEFINITION +pk PACKAGE BODY NULL +connection default; +disconnect conn1; +SET sql_mode=ORACLE; +revoke alter routine on package body test_db.pk from user@localhost; +SET sql_mode=@save_sql_mode; +### +### SHOW CREATE PROCEDURE tests +### +# +### Global "show create routine" test +# +grant show create routine on *.* to user@localhost; +show grants for user@localhost; +Grants for user@localhost +GRANT SHOW CREATE ROUTINE ON *.* TO `user`@`localhost` +GRANT ALL PRIVILEGES ON `test`.* TO `user`@`localhost` +connect conn1, localhost, user, , test; +show create procedure test_db.sp; +Procedure sql_mode Create Procedure character_set_client collation_connection Database Collation +sp STRICT_TRANS_TABLES,ERROR_FOR_DIVISION_BY_ZERO,NO_AUTO_CREATE_USER,NO_ENGINE_SUBSTITUTION CREATE DEFINER=`root`@`localhost` PROCEDURE `sp`() +select 1 latin1 latin1_swedish_ci latin1_swedish_ci +SHOW PROCEDURE STATUS WHERE name="sp"; +Db Name Type Definer Modified Created Security_type Comment character_set_client collation_connection Database Collation +test_db sp PROCEDURE root@localhost # # DEFINER latin1 latin1_swedish_ci latin1_swedish_ci +SELECT ROUTINE_NAME, ROUTINE_DEFINITION from information_schema.ROUTINES where ROUTINE_NAME="sp"; +ROUTINE_NAME ROUTINE_DEFINITION +sp select 1 +show create function test_db.fn; +Function sql_mode Create Function character_set_client collation_connection Database Collation +fn STRICT_TRANS_TABLES,ERROR_FOR_DIVISION_BY_ZERO,NO_AUTO_CREATE_USER,NO_ENGINE_SUBSTITUTION CREATE DEFINER=`root`@`localhost` FUNCTION `fn`() RETURNS int(11) +RETURN 1 latin1 latin1_swedish_ci latin1_swedish_ci +SHOW FUNCTION STATUS WHERE name="fn"; +Db Name Type Definer Modified Created Security_type Comment character_set_client collation_connection Database Collation +test_db fn FUNCTION root@localhost # # DEFINER latin1 latin1_swedish_ci latin1_swedish_ci +SELECT ROUTINE_NAME, ROUTINE_DEFINITION from information_schema.ROUTINES where ROUTINE_NAME="fn"; +ROUTINE_NAME ROUTINE_DEFINITION +fn RETURN 1 +show create package test_db.pk; +Package sql_mode Create Package character_set_client collation_connection Database Collation +pk PIPES_AS_CONCAT,ANSI_QUOTES,IGNORE_SPACE,ORACLE,NO_KEY_OPTIONS,NO_TABLE_OPTIONS,NO_FIELD_OPTIONS,NO_AUTO_CREATE_USER,SIMULTANEOUS_ASSIGNMENT CREATE DEFINER="root"@"localhost" PACKAGE "pk" AS +FUNCTION pkf() RETURN INT; +PROCEDURE pkp(); +END latin1 latin1_swedish_ci latin1_swedish_ci +show create package body test_db.pk; +Package body sql_mode Create Package Body character_set_client collation_connection Database Collation +pk PIPES_AS_CONCAT,ANSI_QUOTES,IGNORE_SPACE,ORACLE,NO_KEY_OPTIONS,NO_TABLE_OPTIONS,NO_FIELD_OPTIONS,NO_AUTO_CREATE_USER,SIMULTANEOUS_ASSIGNMENT CREATE DEFINER="root"@"localhost" PACKAGE BODY "pk" AS +pkv INT:=1; +PROCEDURE pkhp() AS +BEGIN +SELECT pkv FROM DUAL; +END; +FUNCTION pkhf() RETURN INT AS +BEGIN +RETURN pkv; +END; +PROCEDURE pkp() AS +BEGIN +CALL pkhp(); +END; +FUNCTION pkf() RETURN INT AS +BEGIN +RETURN pkhf(); +END; +BEGIN +pkv:=2; +END latin1 latin1_swedish_ci latin1_swedish_ci +SHOW PACKAGE STATUS WHERE name="pk"; +Db Name Type Definer Modified Created Security_type Comment character_set_client collation_connection Database Collation +test_db pk PACKAGE root@localhost # # DEFINER latin1 latin1_swedish_ci latin1_swedish_ci +SELECT ROUTINE_NAME, ROUTINE_TYPE, ROUTINE_DEFINITION from information_schema.ROUTINES where ROUTINE_NAME="pk"; +ROUTINE_NAME ROUTINE_TYPE ROUTINE_DEFINITION +pk PACKAGE AS +FUNCTION pkf() RETURN INT; +PROCEDURE pkp(); +END +pk PACKAGE BODY AS +pkv INT:=1; +PROCEDURE pkhp() AS +BEGIN +SELECT pkv FROM DUAL; +END; +FUNCTION pkhf() RETURN INT AS +BEGIN +RETURN pkv; +END; +PROCEDURE pkp() AS +BEGIN +CALL pkhp(); +END; +FUNCTION pkf() RETURN INT AS +BEGIN +RETURN pkhf(); +END; +BEGIN +pkv:=2; +END +connection default; +disconnect conn1; +revoke show create routine on *.* from user@localhost; +# +### DB-level "show create routine" but other DB test +# +grant show create routine on db_test.* to user@localhost; +show grants for user@localhost; +Grants for user@localhost +GRANT USAGE ON *.* TO `user`@`localhost` +GRANT ALL PRIVILEGES ON `test`.* TO `user`@`localhost` +GRANT SHOW CREATE ROUTINE ON `db_test`.* TO `user`@`localhost` +connect conn1, localhost, user, , test; +show create procedure test_db.sp; +ERROR 42000: PROCEDURE sp does not exist +SHOW PROCEDURE STATUS WHERE name="sp"; +Db Name Type Definer Modified Created Security_type Comment character_set_client collation_connection Database Collation +SELECT ROUTINE_NAME, ROUTINE_DEFINITION from information_schema.ROUTINES where ROUTINE_NAME="sp"; +ROUTINE_NAME ROUTINE_DEFINITION +show create function test_db.fn; +ERROR 42000: FUNCTION fn does not exist +SHOW FUNCTION STATUS WHERE name="fn"; +Db Name Type Definer Modified Created Security_type Comment character_set_client collation_connection Database Collation +SELECT ROUTINE_NAME, ROUTINE_DEFINITION from information_schema.ROUTINES where ROUTINE_NAME="fn"; +ROUTINE_NAME ROUTINE_DEFINITION +show create package test_db.pk; +ERROR 42000: PACKAGE pk does not exist +show create package body test_db.pk; +ERROR 42000: PACKAGE BODY pk does not exist +SHOW PACKAGE STATUS WHERE name="pk"; +Db Name Type Definer Modified Created Security_type Comment character_set_client collation_connection Database Collation +SELECT ROUTINE_NAME, ROUTINE_TYPE, ROUTINE_DEFINITION from information_schema.ROUTINES where ROUTINE_NAME="pk"; +ROUTINE_NAME ROUTINE_TYPE ROUTINE_DEFINITION +connection default; +disconnect conn1; +revoke show create routine on db_test.* from user@localhost; +# +### DB-level "show create routine" test +# +grant show create routine on test_db.* to user@localhost; +show grants for user@localhost; +Grants for user@localhost +GRANT USAGE ON *.* TO `user`@`localhost` +GRANT ALL PRIVILEGES ON `test`.* TO `user`@`localhost` +GRANT SHOW CREATE ROUTINE ON `test_db`.* TO `user`@`localhost` +connect conn1, localhost, user, , test; +show create procedure test_db.sp; +Procedure sql_mode Create Procedure character_set_client collation_connection Database Collation +sp STRICT_TRANS_TABLES,ERROR_FOR_DIVISION_BY_ZERO,NO_AUTO_CREATE_USER,NO_ENGINE_SUBSTITUTION CREATE DEFINER=`root`@`localhost` PROCEDURE `sp`() +select 1 latin1 latin1_swedish_ci latin1_swedish_ci +SHOW PROCEDURE STATUS WHERE name="sp"; +Db Name Type Definer Modified Created Security_type Comment character_set_client collation_connection Database Collation +test_db sp PROCEDURE root@localhost # # DEFINER latin1 latin1_swedish_ci latin1_swedish_ci +SELECT ROUTINE_NAME, ROUTINE_DEFINITION from information_schema.ROUTINES where ROUTINE_NAME="sp"; +ROUTINE_NAME ROUTINE_DEFINITION +sp select 1 +show create function test_db.fn; +Function sql_mode Create Function character_set_client collation_connection Database Collation +fn STRICT_TRANS_TABLES,ERROR_FOR_DIVISION_BY_ZERO,NO_AUTO_CREATE_USER,NO_ENGINE_SUBSTITUTION CREATE DEFINER=`root`@`localhost` FUNCTION `fn`() RETURNS int(11) +RETURN 1 latin1 latin1_swedish_ci latin1_swedish_ci +SHOW FUNCTION STATUS WHERE name="fn"; +Db Name Type Definer Modified Created Security_type Comment character_set_client collation_connection Database Collation +test_db fn FUNCTION root@localhost # # DEFINER latin1 latin1_swedish_ci latin1_swedish_ci +SELECT ROUTINE_NAME, ROUTINE_DEFINITION from information_schema.ROUTINES where ROUTINE_NAME="fn"; +ROUTINE_NAME ROUTINE_DEFINITION +fn RETURN 1 +show create package test_db.pk; +Package sql_mode Create Package character_set_client collation_connection Database Collation +pk PIPES_AS_CONCAT,ANSI_QUOTES,IGNORE_SPACE,ORACLE,NO_KEY_OPTIONS,NO_TABLE_OPTIONS,NO_FIELD_OPTIONS,NO_AUTO_CREATE_USER,SIMULTANEOUS_ASSIGNMENT CREATE DEFINER="root"@"localhost" PACKAGE "pk" AS +FUNCTION pkf() RETURN INT; +PROCEDURE pkp(); +END latin1 latin1_swedish_ci latin1_swedish_ci +show create package body test_db.pk; +Package body sql_mode Create Package Body character_set_client collation_connection Database Collation +pk PIPES_AS_CONCAT,ANSI_QUOTES,IGNORE_SPACE,ORACLE,NO_KEY_OPTIONS,NO_TABLE_OPTIONS,NO_FIELD_OPTIONS,NO_AUTO_CREATE_USER,SIMULTANEOUS_ASSIGNMENT CREATE DEFINER="root"@"localhost" PACKAGE BODY "pk" AS +pkv INT:=1; +PROCEDURE pkhp() AS +BEGIN +SELECT pkv FROM DUAL; +END; +FUNCTION pkhf() RETURN INT AS +BEGIN +RETURN pkv; +END; +PROCEDURE pkp() AS +BEGIN +CALL pkhp(); +END; +FUNCTION pkf() RETURN INT AS +BEGIN +RETURN pkhf(); +END; +BEGIN +pkv:=2; +END latin1 latin1_swedish_ci latin1_swedish_ci +SHOW PACKAGE STATUS WHERE name="pk"; +Db Name Type Definer Modified Created Security_type Comment character_set_client collation_connection Database Collation +test_db pk PACKAGE root@localhost # # DEFINER latin1 latin1_swedish_ci latin1_swedish_ci +SELECT ROUTINE_NAME, ROUTINE_TYPE, ROUTINE_DEFINITION from information_schema.ROUTINES where ROUTINE_NAME="pk"; +ROUTINE_NAME ROUTINE_TYPE ROUTINE_DEFINITION +pk PACKAGE AS +FUNCTION pkf() RETURN INT; +PROCEDURE pkp(); +END +pk PACKAGE BODY AS +pkv INT:=1; +PROCEDURE pkhp() AS +BEGIN +SELECT pkv FROM DUAL; +END; +FUNCTION pkhf() RETURN INT AS +BEGIN +RETURN pkv; +END; +PROCEDURE pkp() AS +BEGIN +CALL pkhp(); +END; +FUNCTION pkf() RETURN INT AS +BEGIN +RETURN pkhf(); +END; +BEGIN +pkv:=2; +END +connection default; +disconnect conn1; +revoke show create routine on test_db.* from user@localhost; +# +### Routine-level "show create routine" PROCEDURE and FUNCTION +# +grant show create routine on procedure test_db.sp to user@localhost; +grant show create routine on function test_db.fn to user@localhost; +connect conn1, localhost, user, , test; +show create procedure test_db.sp; +Procedure sql_mode Create Procedure character_set_client collation_connection Database Collation +sp STRICT_TRANS_TABLES,ERROR_FOR_DIVISION_BY_ZERO,NO_AUTO_CREATE_USER,NO_ENGINE_SUBSTITUTION CREATE DEFINER=`root`@`localhost` PROCEDURE `sp`() +select 1 latin1 latin1_swedish_ci latin1_swedish_ci +SHOW PROCEDURE STATUS WHERE name="sp"; +Db Name Type Definer Modified Created Security_type Comment character_set_client collation_connection Database Collation +test_db sp PROCEDURE root@localhost # # DEFINER latin1 latin1_swedish_ci latin1_swedish_ci +SELECT ROUTINE_NAME, ROUTINE_DEFINITION from information_schema.ROUTINES where ROUTINE_NAME="sp"; +ROUTINE_NAME ROUTINE_DEFINITION +sp select 1 +call test_db.sp(); +ERROR 42000: execute command denied to user 'user'@'localhost' for routine 'test_db.sp' +show create function test_db.fn; +Function sql_mode Create Function character_set_client collation_connection Database Collation +fn STRICT_TRANS_TABLES,ERROR_FOR_DIVISION_BY_ZERO,NO_AUTO_CREATE_USER,NO_ENGINE_SUBSTITUTION CREATE DEFINER=`root`@`localhost` FUNCTION `fn`() RETURNS int(11) +RETURN 1 latin1 latin1_swedish_ci latin1_swedish_ci +SHOW FUNCTION STATUS WHERE name="fn"; +Db Name Type Definer Modified Created Security_type Comment character_set_client collation_connection Database Collation +test_db fn FUNCTION root@localhost # # DEFINER latin1 latin1_swedish_ci latin1_swedish_ci +SELECT ROUTINE_NAME, ROUTINE_DEFINITION from information_schema.ROUTINES where +ROUTINE_NAME="fn"; +ROUTINE_NAME ROUTINE_DEFINITION +fn RETURN 1 +select test_db.fn(); +ERROR 42000: execute command denied to user 'user'@'localhost' for routine 'test_db.fn' +connection default; +disconnect conn1; +revoke show create routine on procedure test_db.sp from user@localhost; +revoke show create routine on function test_db.fn from user@localhost; +# +### Routine-level "show create routine" PACKAGE+ PACKAGE BODY- +# +SET sql_mode=ORACLE; +grant show create routine on package test_db.pk to user@localhost; +SET sql_mode=@save_sql_mode; +connect conn1, localhost, user, , test; +show create package test_db.pk; +Package sql_mode Create Package character_set_client collation_connection Database Collation +pk PIPES_AS_CONCAT,ANSI_QUOTES,IGNORE_SPACE,ORACLE,NO_KEY_OPTIONS,NO_TABLE_OPTIONS,NO_FIELD_OPTIONS,NO_AUTO_CREATE_USER,SIMULTANEOUS_ASSIGNMENT CREATE DEFINER="root"@"localhost" PACKAGE "pk" AS +FUNCTION pkf() RETURN INT; +PROCEDURE pkp(); +END latin1 latin1_swedish_ci latin1_swedish_ci +show create package body test_db.pk; +ERROR 42000: PACKAGE BODY pk does not exist +SHOW PACKAGE STATUS WHERE name="pk"; +Db Name Type Definer Modified Created Security_type Comment character_set_client collation_connection Database Collation +test_db pk PACKAGE root@localhost # # DEFINER latin1 latin1_swedish_ci latin1_swedish_ci +SELECT ROUTINE_NAME, ROUTINE_TYPE, ROUTINE_DEFINITION from information_schema.ROUTINES where ROUTINE_NAME="pk"; +ROUTINE_NAME ROUTINE_TYPE ROUTINE_DEFINITION +pk PACKAGE AS +FUNCTION pkf() RETURN INT; +PROCEDURE pkp(); +END +call test_db.pk.pkp(); +ERROR 42000: execute command denied to user 'user'@'localhost' for routine 'test_db.pk' +select test_db.pk.pkf(); +ERROR 42000: execute command denied to user 'user'@'localhost' for routine 'test_db.pk' +connection default; +disconnect conn1; +SET sql_mode=ORACLE; +revoke show create routine on package test_db.pk from user@localhost; +SET sql_mode=@save_sql_mode; +# +### Routine-level "show create routine" PACKAGE- PACKAGE BODY+ +# +SET sql_mode=ORACLE; +grant show create routine on package body test_db.pk to user@localhost; +SET sql_mode=@save_sql_mode; +connect conn1, localhost, user, , test; +show create package test_db.pk; +ERROR 42000: PACKAGE pk does not exist +show create package body test_db.pk; +Package body sql_mode Create Package Body character_set_client collation_connection Database Collation +pk PIPES_AS_CONCAT,ANSI_QUOTES,IGNORE_SPACE,ORACLE,NO_KEY_OPTIONS,NO_TABLE_OPTIONS,NO_FIELD_OPTIONS,NO_AUTO_CREATE_USER,SIMULTANEOUS_ASSIGNMENT CREATE DEFINER="root"@"localhost" PACKAGE BODY "pk" AS +pkv INT:=1; +PROCEDURE pkhp() AS +BEGIN +SELECT pkv FROM DUAL; +END; +FUNCTION pkhf() RETURN INT AS +BEGIN +RETURN pkv; +END; +PROCEDURE pkp() AS +BEGIN +CALL pkhp(); +END; +FUNCTION pkf() RETURN INT AS +BEGIN +RETURN pkhf(); +END; +BEGIN +pkv:=2; +END latin1 latin1_swedish_ci latin1_swedish_ci +SHOW PACKAGE STATUS WHERE name="pk"; +Db Name Type Definer Modified Created Security_type Comment character_set_client collation_connection Database Collation +SELECT ROUTINE_NAME, ROUTINE_TYPE, ROUTINE_DEFINITION from information_schema.ROUTINES where ROUTINE_NAME="pk"; +ROUTINE_NAME ROUTINE_TYPE ROUTINE_DEFINITION +pk PACKAGE BODY AS +pkv INT:=1; +PROCEDURE pkhp() AS +BEGIN +SELECT pkv FROM DUAL; +END; +FUNCTION pkhf() RETURN INT AS +BEGIN +RETURN pkv; +END; +PROCEDURE pkp() AS +BEGIN +CALL pkhp(); +END; +FUNCTION pkf() RETURN INT AS +BEGIN +RETURN pkhf(); +END; +BEGIN +pkv:=2; +END +call test_db.pk.pkp(); +ERROR 42000: execute command denied to user 'user'@'localhost' for routine 'test_db.pk' +select test_db.pk.pkf(); +ERROR 42000: execute command denied to user 'user'@'localhost' for routine 'test_db.pk' +connection default; +disconnect conn1; +SET sql_mode=ORACLE; +revoke show create routine on package body test_db.pk from user@localhost; +SET sql_mode=@save_sql_mode; +drop user user@localhost; +drop database test_db; +# +### Check owner only rights +# +create user user@localhost; +create database test_db; +use test_db; +create definer=user@localhost procedure test_db.sp() select 1; +CREATE definer=user@localhost FUNCTION test_db.fn() RETURNS INT RETURN 1; +SET sql_mode=ORACLE; +CREATE definer=user@localhost PACKAGE test_db.pk AS +FUNCTION pkf() RETURN INT; +PROCEDURE pkp(); +END; +$$ +CREATE definer=user@localhost PACKAGE BODY test_db.pk AS +pkv INT:=1; +PROCEDURE pkhp() AS +BEGIN +SELECT pkv FROM DUAL; +END; +FUNCTION pkhf() RETURN INT AS +BEGIN +RETURN pkv; +END; +PROCEDURE pkp() AS +BEGIN +CALL pkhp(); +END; +FUNCTION pkf() RETURN INT AS +BEGIN +RETURN pkhf(); +END; +BEGIN +pkv:=2; +END; +$$ +use test; +connect conn1, localhost, user, , "*NO-ONE*"; +show create procedure test_db.sp; +Procedure sql_mode Create Procedure character_set_client collation_connection Database Collation +sp STRICT_TRANS_TABLES,ERROR_FOR_DIVISION_BY_ZERO,NO_AUTO_CREATE_USER,NO_ENGINE_SUBSTITUTION CREATE DEFINER=`user`@`localhost` PROCEDURE `sp`() +select 1 latin1 latin1_swedish_ci latin1_swedish_ci +SHOW PROCEDURE STATUS WHERE name="sp"; +Db Name Type Definer Modified Created Security_type Comment character_set_client collation_connection Database Collation +test_db sp PROCEDURE user@localhost # # DEFINER latin1 latin1_swedish_ci latin1_swedish_ci +SELECT ROUTINE_NAME from information_schema.ROUTINES where ROUTINE_NAME="sp"; +ROUTINE_NAME +sp +show create function test_db.fn; +Function sql_mode Create Function character_set_client collation_connection Database Collation +fn STRICT_TRANS_TABLES,ERROR_FOR_DIVISION_BY_ZERO,NO_AUTO_CREATE_USER,NO_ENGINE_SUBSTITUTION CREATE DEFINER=`user`@`localhost` FUNCTION `fn`() RETURNS int(11) +RETURN 1 latin1 latin1_swedish_ci latin1_swedish_ci +SHOW FUNCTION STATUS WHERE name="fn"; +Db Name Type Definer Modified Created Security_type Comment character_set_client collation_connection Database Collation +test_db fn FUNCTION user@localhost # # DEFINER latin1 latin1_swedish_ci latin1_swedish_ci +SELECT ROUTINE_NAME, ROUTINE_DEFINITION from information_schema.ROUTINES where +ROUTINE_NAME="fn"; +ROUTINE_NAME ROUTINE_DEFINITION +fn RETURN 1 +show create package test_db.pk; +Package sql_mode Create Package character_set_client collation_connection Database Collation +pk PIPES_AS_CONCAT,ANSI_QUOTES,IGNORE_SPACE,ORACLE,NO_KEY_OPTIONS,NO_TABLE_OPTIONS,NO_FIELD_OPTIONS,NO_AUTO_CREATE_USER,SIMULTANEOUS_ASSIGNMENT CREATE DEFINER="user"@"localhost" PACKAGE "pk" AS +FUNCTION pkf() RETURN INT; +PROCEDURE pkp(); +END latin1 latin1_swedish_ci latin1_swedish_ci +show create package body test_db.pk; +Package body sql_mode Create Package Body character_set_client collation_connection Database Collation +pk PIPES_AS_CONCAT,ANSI_QUOTES,IGNORE_SPACE,ORACLE,NO_KEY_OPTIONS,NO_TABLE_OPTIONS,NO_FIELD_OPTIONS,NO_AUTO_CREATE_USER,SIMULTANEOUS_ASSIGNMENT CREATE DEFINER="user"@"localhost" PACKAGE BODY "pk" AS +pkv INT:=1; +PROCEDURE pkhp() AS +BEGIN +SELECT pkv FROM DUAL; +END; +FUNCTION pkhf() RETURN INT AS +BEGIN +RETURN pkv; +END; +PROCEDURE pkp() AS +BEGIN +CALL pkhp(); +END; +FUNCTION pkf() RETURN INT AS +BEGIN +RETURN pkhf(); +END; +BEGIN +pkv:=2; +END latin1 latin1_swedish_ci latin1_swedish_ci +SHOW PACKAGE STATUS WHERE name="pk"; +Db Name Type Definer Modified Created Security_type Comment character_set_client collation_connection Database Collation +test_db pk PACKAGE user@localhost # # DEFINER latin1 latin1_swedish_ci latin1_swedish_ci +SELECT ROUTINE_NAME, ROUTINE_TYPE, ROUTINE_DEFINITION from information_schema.ROUTINES where ROUTINE_NAME="pk"; +ROUTINE_NAME ROUTINE_TYPE ROUTINE_DEFINITION +pk PACKAGE AS +FUNCTION pkf() RETURN INT; +PROCEDURE pkp(); +END +pk PACKAGE BODY AS +pkv INT:=1; +PROCEDURE pkhp() AS +BEGIN +SELECT pkv FROM DUAL; +END; +FUNCTION pkhf() RETURN INT AS +BEGIN +RETURN pkv; +END; +PROCEDURE pkp() AS +BEGIN +CALL pkhp(); +END; +FUNCTION pkf() RETURN INT AS +BEGIN +RETURN pkhf(); +END; +BEGIN +pkv:=2; +END +connection default; +disconnect conn1; +drop user user@localhost; +drop database test_db; +# +# End of 11.3 tests +# diff --git a/mysql-test/main/sp-security.test b/mysql-test/main/sp-security.test index 85f21835c92..af9ba61d614 100644 --- a/mysql-test/main/sp-security.test +++ b/mysql-test/main/sp-security.test @@ -1123,3 +1123,557 @@ drop function f; --echo # --echo # End of 10.6 tests --echo # + +--echo # +--echo # MDEV-29167: new db-level SHOW CREATE ROUTINE privilege +--echo # + +--echo ### +--echo ### SHOW-Like commad test +--echo ### + +SET @save_sql_mode=@@sql_mode; + +--echo # +--echo ### Prepare functions for the test and SHOW-like by root +--echo # + +create database test_db; +use test_db; +create procedure test_db.sp() select 1; +show create procedure test_db.sp; +--replace_column 5 # 6 # +SHOW PROCEDURE STATUS WHERE name="sp"; +SELECT ROUTINE_NAME, ROUTINE_DEFINITION from information_schema.ROUTINES where ROUTINE_NAME="sp"; +CREATE FUNCTION test_db.fn() RETURNS INT RETURN 1; +show create function test_db.fn; +--replace_column 5 # 6 # +SHOW FUNCTION STATUS WHERE name="fn"; +SELECT ROUTINE_NAME, ROUTINE_DEFINITION from information_schema.ROUTINES where ROUTINE_NAME="fn"; + +SET sql_mode=ORACLE; +DELIMITER $$; +CREATE PACKAGE test_db.pk AS + FUNCTION pkf() RETURN INT; + PROCEDURE pkp(); +END; +$$ +CREATE PACKAGE BODY test_db.pk AS + pkv INT:=1; + + PROCEDURE pkhp() AS + BEGIN + SELECT pkv FROM DUAL; + END; + + FUNCTION pkhf() RETURN INT AS + BEGIN + RETURN pkv; + END; + + PROCEDURE pkp() AS + BEGIN + CALL pkhp(); + END; + FUNCTION pkf() RETURN INT AS + BEGIN + RETURN pkhf(); + END; + +BEGIN + pkv:=2; +END; +$$ +DELIMITER ;$$ + +SET sql_mode=@save_sql_mode; +show create package test_db.pk; +show create package body test_db.pk; +--replace_column 5 # 6 # +SHOW PACKAGE STATUS WHERE name="pk"; +SELECT ROUTINE_NAME, ROUTINE_TYPE, ROUTINE_DEFINITION from information_schema.ROUTINES where ROUTINE_NAME="pk"; + + +use test; + + +--echo ### +--echo ### Pre-"SHOW-CREATE-ROUTINE" behaviour tests +--echo ### + + +--echo # +--echo ### Rights on mysql.proc +--echo # + +create user user@localhost; +grant all privileges on mysql.* to user@localhost; +grant all privileges on test.* to user@localhost; + +connect conn1, localhost, user, , test; + +show create procedure test_db.sp; +--replace_column 5 # 6 # +SHOW PROCEDURE STATUS WHERE name="sp"; +SELECT ROUTINE_NAME from information_schema.ROUTINES where ROUTINE_NAME="sp"; +show create function test_db.fn; +--replace_column 5 # 6 # +SHOW FUNCTION STATUS WHERE name="fn"; +SELECT ROUTINE_NAME, ROUTINE_DEFINITION from information_schema.ROUTINES where +ROUTINE_NAME="fn"; +show create package test_db.pk; +show create package body test_db.pk; +--replace_column 5 # 6 # +SHOW PACKAGE STATUS WHERE name="pk"; +SELECT ROUTINE_NAME, ROUTINE_TYPE, ROUTINE_DEFINITION from information_schema.ROUTINES where ROUTINE_NAME="pk"; + +connection default; +disconnect conn1; + +revoke all privileges on mysql.* from user@localhost; + + +--echo # +--echo ### No privileges +--echo # + +connect conn1, localhost, user, , test; + +--error ER_SP_DOES_NOT_EXIST +show create procedure test_db.sp; +--replace_column 5 # 6 # +SHOW PROCEDURE STATUS WHERE name="sp"; +SELECT ROUTINE_NAME from information_schema.ROUTINES where ROUTINE_NAME="sp"; +--error ER_SP_DOES_NOT_EXIST +show create function test_db.fn; +--replace_column 5 # 6 # +SHOW FUNCTION STATUS WHERE name="fn"; +SELECT ROUTINE_NAME, ROUTINE_DEFINITION from information_schema.ROUTINES where +ROUTINE_NAME="fn"; +--error ER_SP_DOES_NOT_EXIST +show create package test_db.pk; +--error ER_SP_DOES_NOT_EXIST +show create package body test_db.pk; +--replace_column 5 # 6 # +SHOW PACKAGE STATUS WHERE name="pk"; +SELECT ROUTINE_NAME, ROUTINE_TYPE, ROUTINE_DEFINITION from information_schema.ROUTINES where ROUTINE_NAME="pk"; + +connection default; +disconnect conn1; + +--echo # +--echo ### Execute provilege PROCEDURE/FUNCTION +--echo # + +grant execute on procedure test_db.sp to user@localhost; +grant execute on function test_db.fn to user@localhost; + +connect conn1, localhost, user, , test; + +show create procedure test_db.sp; +--replace_column 5 # 6 # +SHOW PROCEDURE STATUS WHERE name="sp"; +SELECT ROUTINE_NAME from information_schema.ROUTINES where ROUTINE_NAME="sp"; +call test_db.sp(); +show create function test_db.fn; +--replace_column 5 # 6 # +SHOW FUNCTION STATUS WHERE name="fn"; +SELECT ROUTINE_NAME, ROUTINE_DEFINITION from information_schema.ROUTINES where +ROUTINE_NAME="fn"; +select test_db.fn(); + +connection default; +disconnect conn1; + +revoke execute on procedure test_db.sp from user@localhost; +revoke execute on function test_db.fn from user@localhost; + +--echo # +--echo ### Execute provilege PACKAGE+ PACKAGE BODY- +--echo # + +SET sql_mode=ORACLE; +grant execute on package test_db.pk to user@localhost; +SET sql_mode=@save_sql_mode; + +connect conn1, localhost, user, , test; + +show create package test_db.pk; +--error ER_SP_DOES_NOT_EXIST +show create package body test_db.pk; +--replace_column 5 # 6 # +SHOW PACKAGE STATUS WHERE name="pk"; +SELECT ROUTINE_NAME, ROUTINE_TYPE, ROUTINE_DEFINITION from information_schema.ROUTINES where ROUTINE_NAME="pk"; +--error ER_PROCACCESS_DENIED_ERROR +call test_db.pk.pkp(); +--error ER_PROCACCESS_DENIED_ERROR +select test_db.pk.pkf(); + +connection default; +disconnect conn1; + +SET sql_mode=ORACLE; +revoke execute on package test_db.pk from user@localhost; +SET sql_mode=@save_sql_mode; + + +--echo # +--echo ### Execute provilege PACKAGE- PACKAGE BODY+ +--echo # + +SET sql_mode=ORACLE; +grant execute on package body test_db.pk to user@localhost; +SET sql_mode=@save_sql_mode; + +connect conn1, localhost, user, , test; + +--error ER_SP_DOES_NOT_EXIST +show create package test_db.pk; +show create package body test_db.pk; +--replace_column 5 # 6 # +SHOW PACKAGE STATUS WHERE name="pk"; +SELECT ROUTINE_NAME, ROUTINE_TYPE, ROUTINE_DEFINITION from information_schema.ROUTINES where ROUTINE_NAME="pk"; +call test_db.pk.pkp(); +select test_db.pk.pkf(); + +connection default; +disconnect conn1; + +SET sql_mode=ORACLE; +revoke execute on package body test_db.pk from user@localhost; +SET sql_mode=@save_sql_mode; + +--echo # +--echo ### Alter routine provilege PROCEDURE/FUNCTION +--echo # + +grant alter routine on procedure test_db.sp to user@localhost; +grant alter routine on function test_db.fn to user@localhost; + +connect conn1, localhost, user, , test; + +show create procedure test_db.sp; +--replace_column 5 # 6 # +SHOW PROCEDURE STATUS WHERE name="sp"; +SELECT ROUTINE_NAME from information_schema.ROUTINES where ROUTINE_NAME="sp"; +show create function test_db.fn; +--replace_column 5 # 6 # +SHOW FUNCTION STATUS WHERE name="fn"; +SELECT ROUTINE_NAME, ROUTINE_DEFINITION from information_schema.ROUTINES where +ROUTINE_NAME="fn"; + +connection default; +disconnect conn1; + + +revoke alter routine on procedure test_db.sp from user@localhost; +revoke alter routine on function test_db.fn from user@localhost; + +--echo # +--echo ### Alter routine provilege PACKAGE+ PACKAGE BODY- +--echo # + +SET sql_mode=ORACLE; +grant alter routine on package test_db.pk to user@localhost; +SET sql_mode=@save_sql_mode; + +connect conn1, localhost, user, , test; + +show create package test_db.pk; +--error ER_SP_DOES_NOT_EXIST +show create package body test_db.pk; +--replace_column 5 # 6 # +SHOW PACKAGE STATUS WHERE name="pk"; +SELECT ROUTINE_NAME, ROUTINE_TYPE, ROUTINE_DEFINITION from information_schema.ROUTINES where ROUTINE_NAME="pk"; + +connection default; +disconnect conn1; + +SET sql_mode=ORACLE; +revoke alter routine on package test_db.pk from user@localhost; +SET sql_mode=@save_sql_mode; + + +--echo # +--echo ### Alter routine provilege PACKAGE+ PACKAGE BODY- +--echo # + +SET sql_mode=ORACLE; +grant alter routine on package body test_db.pk to user@localhost; +SET sql_mode=@save_sql_mode; + +connect conn1, localhost, user, , test; + +--error ER_SP_DOES_NOT_EXIST +show create package test_db.pk; +show create package body test_db.pk; +--replace_column 5 # 6 # +SHOW PACKAGE STATUS WHERE name="pk"; +SELECT ROUTINE_NAME, ROUTINE_TYPE, ROUTINE_DEFINITION from information_schema.ROUTINES where ROUTINE_NAME="pk"; + +connection default; +disconnect conn1; + +SET sql_mode=ORACLE; +revoke alter routine on package body test_db.pk from user@localhost; +SET sql_mode=@save_sql_mode; + + +--echo ### +--echo ### SHOW CREATE PROCEDURE tests +--echo ### + + +--echo # +--echo ### Global "show create routine" test +--echo # + +grant show create routine on *.* to user@localhost; +show grants for user@localhost; + +connect conn1, localhost, user, , test; + +show create procedure test_db.sp; +--replace_column 5 # 6 # +SHOW PROCEDURE STATUS WHERE name="sp"; +SELECT ROUTINE_NAME, ROUTINE_DEFINITION from information_schema.ROUTINES where ROUTINE_NAME="sp"; +show create function test_db.fn; +--replace_column 5 # 6 # +SHOW FUNCTION STATUS WHERE name="fn"; +SELECT ROUTINE_NAME, ROUTINE_DEFINITION from information_schema.ROUTINES where ROUTINE_NAME="fn"; +show create package test_db.pk; +show create package body test_db.pk; +--replace_column 5 # 6 # +SHOW PACKAGE STATUS WHERE name="pk"; +SELECT ROUTINE_NAME, ROUTINE_TYPE, ROUTINE_DEFINITION from information_schema.ROUTINES where ROUTINE_NAME="pk"; + +connection default; +disconnect conn1; + +revoke show create routine on *.* from user@localhost; + +--echo # +--echo ### DB-level "show create routine" but other DB test +--echo # + +grant show create routine on db_test.* to user@localhost; +show grants for user@localhost; + +connect conn1, localhost, user, , test; + +--error ER_SP_DOES_NOT_EXIST +show create procedure test_db.sp; +--replace_column 5 # 6 # +SHOW PROCEDURE STATUS WHERE name="sp"; +SELECT ROUTINE_NAME, ROUTINE_DEFINITION from information_schema.ROUTINES where ROUTINE_NAME="sp"; +--error ER_SP_DOES_NOT_EXIST +show create function test_db.fn; +--replace_column 5 # 6 # +SHOW FUNCTION STATUS WHERE name="fn"; +SELECT ROUTINE_NAME, ROUTINE_DEFINITION from information_schema.ROUTINES where ROUTINE_NAME="fn"; +--error ER_SP_DOES_NOT_EXIST +show create package test_db.pk; +--error ER_SP_DOES_NOT_EXIST +show create package body test_db.pk; +--replace_column 5 # 6 # +SHOW PACKAGE STATUS WHERE name="pk"; +SELECT ROUTINE_NAME, ROUTINE_TYPE, ROUTINE_DEFINITION from information_schema.ROUTINES where ROUTINE_NAME="pk"; + +connection default; +disconnect conn1; + +revoke show create routine on db_test.* from user@localhost; + +--echo # +--echo ### DB-level "show create routine" test +--echo # + +grant show create routine on test_db.* to user@localhost; +show grants for user@localhost; + +connect conn1, localhost, user, , test; + +show create procedure test_db.sp; +--replace_column 5 # 6 # +SHOW PROCEDURE STATUS WHERE name="sp"; +SELECT ROUTINE_NAME, ROUTINE_DEFINITION from information_schema.ROUTINES where ROUTINE_NAME="sp"; +show create function test_db.fn; +--replace_column 5 # 6 # +SHOW FUNCTION STATUS WHERE name="fn"; +SELECT ROUTINE_NAME, ROUTINE_DEFINITION from information_schema.ROUTINES where ROUTINE_NAME="fn"; +show create package test_db.pk; +show create package body test_db.pk; +--replace_column 5 # 6 # +SHOW PACKAGE STATUS WHERE name="pk"; +SELECT ROUTINE_NAME, ROUTINE_TYPE, ROUTINE_DEFINITION from information_schema.ROUTINES where ROUTINE_NAME="pk"; + +connection default; +disconnect conn1; + +revoke show create routine on test_db.* from user@localhost; + + +--echo # +--echo ### Routine-level "show create routine" PROCEDURE and FUNCTION +--echo # + +grant show create routine on procedure test_db.sp to user@localhost; +grant show create routine on function test_db.fn to user@localhost; + +connect conn1, localhost, user, , test; + +show create procedure test_db.sp; +--replace_column 5 # 6 # +SHOW PROCEDURE STATUS WHERE name="sp"; +SELECT ROUTINE_NAME, ROUTINE_DEFINITION from information_schema.ROUTINES where ROUTINE_NAME="sp"; +-- error ER_PROCACCESS_DENIED_ERROR +call test_db.sp(); +show create function test_db.fn; +--replace_column 5 # 6 # +SHOW FUNCTION STATUS WHERE name="fn"; +SELECT ROUTINE_NAME, ROUTINE_DEFINITION from information_schema.ROUTINES where +ROUTINE_NAME="fn"; +-- error ER_PROCACCESS_DENIED_ERROR +select test_db.fn(); + +connection default; +disconnect conn1; + +revoke show create routine on procedure test_db.sp from user@localhost; +revoke show create routine on function test_db.fn from user@localhost; + + +--echo # +--echo ### Routine-level "show create routine" PACKAGE+ PACKAGE BODY- +--echo # + +SET sql_mode=ORACLE; +grant show create routine on package test_db.pk to user@localhost; +SET sql_mode=@save_sql_mode; + +connect conn1, localhost, user, , test; + +show create package test_db.pk; +--error ER_SP_DOES_NOT_EXIST +show create package body test_db.pk; +--replace_column 5 # 6 # +SHOW PACKAGE STATUS WHERE name="pk"; +SELECT ROUTINE_NAME, ROUTINE_TYPE, ROUTINE_DEFINITION from information_schema.ROUTINES where ROUTINE_NAME="pk"; +--error ER_PROCACCESS_DENIED_ERROR +call test_db.pk.pkp(); +--error ER_PROCACCESS_DENIED_ERROR +select test_db.pk.pkf(); + +connection default; +disconnect conn1; + +SET sql_mode=ORACLE; +revoke show create routine on package test_db.pk from user@localhost; +SET sql_mode=@save_sql_mode; + + +--echo # +--echo ### Routine-level "show create routine" PACKAGE- PACKAGE BODY+ +--echo # + +SET sql_mode=ORACLE; +grant show create routine on package body test_db.pk to user@localhost; +SET sql_mode=@save_sql_mode; + + +connect conn1, localhost, user, , test; + +--error ER_SP_DOES_NOT_EXIST +show create package test_db.pk; +show create package body test_db.pk; +--replace_column 5 # 6 # +SHOW PACKAGE STATUS WHERE name="pk"; +SELECT ROUTINE_NAME, ROUTINE_TYPE, ROUTINE_DEFINITION from information_schema.ROUTINES where ROUTINE_NAME="pk"; +--error ER_PROCACCESS_DENIED_ERROR +call test_db.pk.pkp(); +--error ER_PROCACCESS_DENIED_ERROR +select test_db.pk.pkf(); + +connection default; +disconnect conn1; + +SET sql_mode=ORACLE; +revoke show create routine on package body test_db.pk from user@localhost; +SET sql_mode=@save_sql_mode; + +drop user user@localhost; +drop database test_db; + +--echo # +--echo ### Check owner only rights +--echo # + +create user user@localhost; +create database test_db; +use test_db; +create definer=user@localhost procedure test_db.sp() select 1; +CREATE definer=user@localhost FUNCTION test_db.fn() RETURNS INT RETURN 1; +SET sql_mode=ORACLE; +DELIMITER $$; +CREATE definer=user@localhost PACKAGE test_db.pk AS + FUNCTION pkf() RETURN INT; + PROCEDURE pkp(); +END; +$$ +CREATE definer=user@localhost PACKAGE BODY test_db.pk AS + pkv INT:=1; + + PROCEDURE pkhp() AS + BEGIN + SELECT pkv FROM DUAL; + END; + + FUNCTION pkhf() RETURN INT AS + BEGIN + RETURN pkv; + END; + + PROCEDURE pkp() AS + BEGIN + CALL pkhp(); + END; + FUNCTION pkf() RETURN INT AS + BEGIN + RETURN pkhf(); + END; + +BEGIN + pkv:=2; +END; +$$ +DELIMITER ;$$ + +use test; + + +connect conn1, localhost, user, , "*NO-ONE*"; + +show create procedure test_db.sp; +--replace_column 5 # 6 # +SHOW PROCEDURE STATUS WHERE name="sp"; +SELECT ROUTINE_NAME from information_schema.ROUTINES where ROUTINE_NAME="sp"; +show create function test_db.fn; +--replace_column 5 # 6 # +SHOW FUNCTION STATUS WHERE name="fn"; +SELECT ROUTINE_NAME, ROUTINE_DEFINITION from information_schema.ROUTINES where +ROUTINE_NAME="fn"; +show create package test_db.pk; +show create package body test_db.pk; +--replace_column 5 # 6 # +SHOW PACKAGE STATUS WHERE name="pk"; +SELECT ROUTINE_NAME, ROUTINE_TYPE, ROUTINE_DEFINITION from information_schema.ROUTINES where ROUTINE_NAME="pk"; + +connection default; +disconnect conn1; + +drop user user@localhost; +drop database test_db; + +--echo # +--echo # End of 11.3 tests +--echo # diff --git a/mysql-test/main/sp.result b/mysql-test/main/sp.result index c27fe9ac11a..77af394fae1 100644 --- a/mysql-test/main/sp.result +++ b/mysql-test/main/sp.result @@ -8923,6 +8923,31 @@ CREATE TABLE t1 (a INT); CREATE PROCEDURE p1() SELECT 1 FROM t1 PROCEDURE ANALYSE( 10, (SELECT a FROM t1)); ERROR 42000: PROCEDURE does not support subqueries or stored functions DROP TABLE t1; +# +# MDEV-23902: MariaDB crash on calling function +# +CREATE FUNCTION f2 () RETURNS VARCHAR(1) +BEGIN +DECLARE rec1 ROW TYPE OF v1; +SELECT z INTO rec1 FROM v1; +RETURN 1; +END| +CREATE FUNCTION f1 () RETURNS VARCHAR(1) RETURN f2() ; +CREATE FUNCTION f3 () RETURNS VARCHAR(1) RETURN f_not_exist(); +CREATE VIEW v1 AS SELECT f3() z; +SELECT f1(); +ERROR HY000: View 'test.v1' references invalid table(s) or column(s) or function(s) or definer/invoker of view lack rights to use them +# Check that crash doen't happen in case f3 completes with success. +DROP FUNCTION f3; +CREATE FUNCTION f3 () RETURNS VARCHAR(1) RETURN '!'; +SELECT f1(); +f1() +1 +# Clean up +DROP FUNCTION f1; +DROP FUNCTION f2; +DROP FUNCTION f3; +DROP VIEW v1; # End of 10.4 tests # # diff --git a/mysql-test/main/sp.test b/mysql-test/main/sp.test index 835803d2989..6882eecd9e8 100644 --- a/mysql-test/main/sp.test +++ b/mysql-test/main/sp.test @@ -10533,6 +10533,38 @@ CREATE PROCEDURE p1() SELECT 1 FROM t1 PROCEDURE ANALYSE( 10, (SELECT a FROM t1) DROP TABLE t1; +--echo # +--echo # MDEV-23902: MariaDB crash on calling function +--echo # + +--delimiter | +CREATE FUNCTION f2 () RETURNS VARCHAR(1) +BEGIN + DECLARE rec1 ROW TYPE OF v1; + SELECT z INTO rec1 FROM v1; + RETURN 1; +END| +--delimiter ; + +CREATE FUNCTION f1 () RETURNS VARCHAR(1) RETURN f2() ; +CREATE FUNCTION f3 () RETURNS VARCHAR(1) RETURN f_not_exist(); +CREATE VIEW v1 AS SELECT f3() z; + +--error ER_VIEW_INVALID +SELECT f1(); + +--echo # Check that crash doen't happen in case f3 completes with success. +DROP FUNCTION f3; +CREATE FUNCTION f3 () RETURNS VARCHAR(1) RETURN '!'; + +SELECT f1(); + +--echo # Clean up +DROP FUNCTION f1; +DROP FUNCTION f2; +DROP FUNCTION f3; +DROP VIEW v1; + --echo # End of 10.4 tests --echo # diff --git a/mysql-test/main/sql_mode.result b/mysql-test/main/sql_mode.result index 31308cd6a2f..449534da25e 100644 --- a/mysql-test/main/sql_mode.result +++ b/mysql-test/main/sql_mode.result @@ -535,7 +535,7 @@ SET SESSION SQL_MODE = @OLD_SQL_MODE; DROP USER 'user_no_PCTFL'@'localhost'; FLUSH PRIVILEGES; SELECT * FROM mysql.db WHERE Host = 'localhost' AND User LIKE 'user_%PCTFL'; -Host Db User Select_priv Insert_priv Update_priv Delete_priv Create_priv Drop_priv Grant_priv References_priv Index_priv Alter_priv Create_tmp_table_priv Lock_tables_priv Create_view_priv Show_view_priv Create_routine_priv Alter_routine_priv Execute_priv Event_priv Trigger_priv Delete_history_priv +Host Db User Select_priv Insert_priv Update_priv Delete_priv Create_priv Drop_priv Grant_priv References_priv Index_priv Alter_priv Create_tmp_table_priv Lock_tables_priv Create_view_priv Show_view_priv Create_routine_priv Alter_routine_priv Execute_priv Event_priv Trigger_priv Delete_history_priv Show_create_routine_priv SELECT * FROM mysql.tables_priv WHERE Host = 'localhost' AND User LIKE 'user_%PCTFL'; Host Db User Table_name Grantor Timestamp Table_priv Column_priv SELECT * FROM mysql.columns_priv WHERE Host = 'localhost' AND User LIKE 'user_%PCTFL'; diff --git a/mysql-test/main/ssl_cipher.result b/mysql-test/main/ssl_cipher.result index 42f37f488e7..d549ec7d2b4 100644 --- a/mysql-test/main/ssl_cipher.result +++ b/mysql-test/main/ssl_cipher.result @@ -66,3 +66,5 @@ VARIABLE_VALUE like '%AES128-SHA%' 1 disconnect ssl_con; connection default; +call mtr.add_suppression("TLSv1.0 and TLSv1.1 are insecure"); +FOUND 2 /TLSv1.0 and TLSv1.1 are insecure/ in mysqld.1.err diff --git a/mysql-test/main/ssl_cipher.test b/mysql-test/main/ssl_cipher.test index 4671b085ce7..0d33ec5d5e0 100644 --- a/mysql-test/main/ssl_cipher.test +++ b/mysql-test/main/ssl_cipher.test @@ -2,6 +2,11 @@ # Various tests that require setting of a specific ssl_cipher # which currently doesn't work in OpenSSL 1.1.1 # + +--disable_query_log +CALL mtr.add_suppression("are insecure"); +--enable_query_log + --source include/have_ssl_communication.inc if (`select @@version_ssl_library like 'OpenSSL 1.1.1%'`) { @@ -101,3 +106,9 @@ SHOW STATUS LIKE 'Ssl_cipher'; SELECT VARIABLE_VALUE like '%AES128-SHA%' FROM INFORMATION_SCHEMA.SESSION_STATUS WHERE VARIABLE_NAME='Ssl_cipher_list'; disconnect ssl_con; connection default; + +# MDEV-31369 Disable TLS v1.0 and 1.1 for MariaDB +call mtr.add_suppression("TLSv1.0 and TLSv1.1 are insecure"); +--let SEARCH_FILE=$MYSQLTEST_VARDIR/log/mysqld.1.err +--let SEARCH_PATTERN= TLSv1.0 and TLSv1.1 are insecure +--source include/search_pattern_in_file.inc diff --git a/mysql-test/main/stat_tables.result b/mysql-test/main/stat_tables.result index a6642d66fb7..be1a88e9743 100644 --- a/mysql-test/main/stat_tables.result +++ b/mysql-test/main/stat_tables.result @@ -562,14 +562,14 @@ test.t1 analyze Warning Engine-independent statistics are not collected for colu test.t1 analyze status OK SELECT * FROM mysql.column_stats; db_name table_name column_name min_value max_value nulls_ratio avg_length avg_frequency hist_size hist_type histogram -test t1 pk 1 2 0.0000 4.0000 1.0000 0 NULL NULL +test t1 pk 1 2 0.0000 4.0000 1.0000 NULL NULL NULL DELETE FROM mysql.column_stats WHERE db_name='test' AND table_name='t1' AND column_name='t'; INSERT INTO mysql.column_stats VALUES ('test','t1','t','bar','foo', 0.0, 3.0, 1.0, 0, NULL, NULL); SELECT * FROM mysql.column_stats; db_name table_name column_name min_value max_value nulls_ratio avg_length avg_frequency hist_size hist_type histogram -test t1 pk 1 2 0.0000 4.0000 1.0000 0 NULL NULL +test t1 pk 1 2 0.0000 4.0000 1.0000 NULL NULL NULL test t1 t bar foo 0.0000 3.0000 1.0000 0 NULL NULL SELECT pk FROM t1; pk @@ -593,7 +593,7 @@ pk c 2 bar SELECT * FROM mysql.column_stats; db_name table_name column_name min_value max_value nulls_ratio avg_length avg_frequency hist_size hist_type histogram -test t1 pk 1 2 0.0000 4.0000 1.0000 0 NULL NULL +test t1 pk 1 2 0.0000 4.0000 1.0000 NULL NULL NULL test t1 c bar foo 0.0000 3.0000 1.0000 0 NULL NULL CREATE OR REPLACE TABLE t1 (pk int PRIMARY KEY, a char(7)); SELECT * FROM t1; @@ -923,4 +923,82 @@ id select_type table type possible_keys key key_len ref rows r_rows filtered r_f 1 SIMPLE t1 ALL NULL NULL NULL NULL 10 10.00 2.78 10.00 Using where drop table t1; set @@global.histogram_size=@save_histogram_size; +# # End of 10.4 tests +# +# +# MDEV-29693 ANALYZE TABLE still flushes table definition cache +# when engine-independent statistics is used +# +create table t1 (a int); +insert into t1 select seq from seq_0_to_99; +analyze table t1 persistent for all; +Table Op Msg_type Msg_text +test.t1 analyze status Engine-independent statistics collected +test.t1 analyze status OK +analyze table t1 persistent for all; +Table Op Msg_type Msg_text +test.t1 analyze status Engine-independent statistics collected +test.t1 analyze status Table is already up to date +explain extended select count(*) from t1 where a < 50; +id select_type table type possible_keys key key_len ref rows filtered Extra +1 SIMPLE t1 ALL NULL NULL NULL NULL 100 50.51 Using where +Warnings: +Note 1003 select count(0) AS `count(*)` from `test`.`t1` where `test`.`t1`.`a` < 50 +connect con1, localhost, root,,; +connection con1; +explain extended select count(*) from t1 where a < 50; +id select_type table type possible_keys key key_len ref rows filtered Extra +1 SIMPLE t1 ALL NULL NULL NULL NULL 100 50.51 Using where +Warnings: +Note 1003 select count(0) AS `count(*)` from `test`.`t1` where `test`.`t1`.`a` < 50 +connection default; +update t1 set a= a +100; +# Explain shows outdated statistics: +explain extended select count(*) from t1 where a < 50; +id select_type table type possible_keys key key_len ref rows filtered Extra +1 SIMPLE t1 ALL NULL NULL NULL NULL 100 50.51 Using where +Warnings: +Note 1003 select count(0) AS `count(*)` from `test`.`t1` where `test`.`t1`.`a` < 50 +connection con1; +explain extended select count(*) from t1 where a < 50; +id select_type table type possible_keys key key_len ref rows filtered Extra +1 SIMPLE t1 ALL NULL NULL NULL NULL 100 50.51 Using where +Warnings: +Note 1003 select count(0) AS `count(*)` from `test`.`t1` where `test`.`t1`.`a` < 50 +connection default; +analyze table t1 persistent for all; +Table Op Msg_type Msg_text +test.t1 analyze status Engine-independent statistics collected +test.t1 analyze status OK +# Now explain shows updated statistics: +explain extended select count(*) from t1 where a < 50; +id select_type table type possible_keys key key_len ref rows filtered Extra +1 SIMPLE t1 ALL NULL NULL NULL NULL 100 1.00 Using where +Warnings: +Note 1003 select count(0) AS `count(*)` from `test`.`t1` where `test`.`t1`.`a` < 50 +connection con1; +explain extended select count(*) from t1 where a < 50; +id select_type table type possible_keys key key_len ref rows filtered Extra +1 SIMPLE t1 ALL NULL NULL NULL NULL 100 1.00 Using where +Warnings: +Note 1003 select count(0) AS `count(*)` from `test`.`t1` where `test`.`t1`.`a` < 50 +connection con1; +# Run update and analyze in con1: +update t1 set a= a - 150; +analyze table t1 persistent for all; +Table Op Msg_type Msg_text +test.t1 analyze status Engine-independent statistics collected +test.t1 analyze status OK +connection default; +# Explain shows updated statistics: +explain extended select count(*) from t1 where a < 50; +id select_type table type possible_keys key key_len ref rows filtered Extra +1 SIMPLE t1 ALL NULL NULL NULL NULL 100 100.00 Using where +Warnings: +Note 1003 select count(0) AS `count(*)` from `test`.`t1` where `test`.`t1`.`a` < 50 +disconnect con1; +drop table t1; +# +# End of 10.6 tests +# diff --git a/mysql-test/main/stat_tables.test b/mysql-test/main/stat_tables.test index 895db3ce72e..8333613dce4 100644 --- a/mysql-test/main/stat_tables.test +++ b/mysql-test/main/stat_tables.test @@ -1,7 +1,6 @@ # Tests will be skipped for the view protocol because the view protocol creates # an additional util connection and other statistics data --- source include/no_view_protocol.inc - +--source include/no_view_protocol.inc --source include/have_stat_tables.inc --source include/have_partition.inc --source include/have_sequence.inc @@ -641,4 +640,64 @@ drop table t1; set @@global.histogram_size=@save_histogram_size; +--echo # --echo # End of 10.4 tests +--echo # + +--echo # +--echo # MDEV-29693 ANALYZE TABLE still flushes table definition cache +--echo # when engine-independent statistics is used +--echo # + +create table t1 (a int); +insert into t1 select seq from seq_0_to_99; +analyze table t1 persistent for all; +analyze table t1 persistent for all; + +explain extended select count(*) from t1 where a < 50; + +connect (con1, localhost, root,,); +--connection con1 +explain extended select count(*) from t1 where a < 50; + +let $open_tables=`select variable_value from information_schema.global_status where variable_name="OPENED_TABLES"`; + +--connection default +update t1 set a= a +100; + +--echo # Explain shows outdated statistics: +explain extended select count(*) from t1 where a < 50; +--connection con1 +explain extended select count(*) from t1 where a < 50; + +--connection default +analyze table t1 persistent for all; +--echo # Now explain shows updated statistics: +explain extended select count(*) from t1 where a < 50; +--connection con1 +explain extended select count(*) from t1 where a < 50; + +--connection con1 +--echo # Run update and analyze in con1: +update t1 set a= a - 150; +analyze table t1 persistent for all; + +--connection default +--echo # Explain shows updated statistics: +explain extended select count(*) from t1 where a < 50; + +disconnect con1; + +let $new_open_tables=`select variable_value from information_schema.global_status where variable_name="OPENED_TABLES"`; + +if ($open_tables != $new_open_tables) +{ +--let $diff=`select $new_open_tables - $open_tables` +--echo "Fail: Test opened $diff new tables, 0 was expected" +} + +drop table t1; + +--echo # +--echo # End of 10.6 tests +--echo # diff --git a/mysql-test/main/stat_tables_flush.result b/mysql-test/main/stat_tables_flush.result new file mode 100644 index 00000000000..36d847977b9 --- /dev/null +++ b/mysql-test/main/stat_tables_flush.result @@ -0,0 +1,190 @@ +# +# Check that ANALYZE TABLE is remembered by MyISAM and Aria +# +create table t1 (a int) engine=myisam; +insert into t1 select seq from seq_0_to_99; +analyze table t1 persistent for all; +Table Op Msg_type Msg_text +test.t1 analyze status Engine-independent statistics collected +test.t1 analyze status OK +flush tables; +analyze table t1 persistent for all; +Table Op Msg_type Msg_text +test.t1 analyze status Engine-independent statistics collected +test.t1 analyze status Table is already up to date +update t1 set a=100 where a=1; +analyze table t1 persistent for all; +Table Op Msg_type Msg_text +test.t1 analyze status Engine-independent statistics collected +test.t1 analyze status OK +update t1 set a=100 where a=2; +flush tables; +analyze table t1 persistent for all; +Table Op Msg_type Msg_text +test.t1 analyze status Engine-independent statistics collected +test.t1 analyze status OK +# Aria transactional=0 +ALTER TABLE t1 ENGINE=aria transactional=0; +analyze table t1 persistent for all; +Table Op Msg_type Msg_text +test.t1 analyze status Engine-independent statistics collected +test.t1 analyze status OK +update t1 set a=100 where a=10; +analyze table t1 persistent for all; +Table Op Msg_type Msg_text +test.t1 analyze status Engine-independent statistics collected +test.t1 analyze status OK +analyze table t1 persistent for all; +Table Op Msg_type Msg_text +test.t1 analyze status Engine-independent statistics collected +test.t1 analyze status Table is already up to date +flush tables; +analyze table t1 persistent for all; +Table Op Msg_type Msg_text +test.t1 analyze status Engine-independent statistics collected +test.t1 analyze status Table is already up to date +update t1 set a=100 where a=11; +analyze table t1 persistent for all; +Table Op Msg_type Msg_text +test.t1 analyze status Engine-independent statistics collected +test.t1 analyze status OK +update t1 set a=100 where a=12; +flush tables; +analyze table t1 persistent for all; +Table Op Msg_type Msg_text +test.t1 analyze status Engine-independent statistics collected +test.t1 analyze status Table is already up to date +# Aria transactional=1 +ALTER TABLE t1 ENGINE=aria transactional=1; +analyze table t1 persistent for all; +Table Op Msg_type Msg_text +test.t1 analyze status Engine-independent statistics collected +test.t1 analyze status OK +update t1 set a=100 where a=20; +analyze table t1 persistent for all; +Table Op Msg_type Msg_text +test.t1 analyze status Engine-independent statistics collected +test.t1 analyze status OK +analyze table t1 persistent for all; +Table Op Msg_type Msg_text +test.t1 analyze status Engine-independent statistics collected +test.t1 analyze status Table is already up to date +flush tables; +analyze table t1 persistent for all; +Table Op Msg_type Msg_text +test.t1 analyze status Engine-independent statistics collected +test.t1 analyze status Table is already up to date +update t1 set a=100 where a=21; +analyze table t1 persistent for all; +Table Op Msg_type Msg_text +test.t1 analyze status Engine-independent statistics collected +test.t1 analyze status OK +update t1 set a=100 where a=22; +flush tables; +analyze table t1 persistent for all; +Table Op Msg_type Msg_text +test.t1 analyze status Engine-independent statistics collected +test.t1 analyze status OK +drop table t1; +# +# Test that histograms are read after flush +# +create table t1 (a int); +insert into t1 select seq from seq_1_to_10; +insert into t1 select A.seq from seq_10_to_20 A, seq_1_to_9 B; +analyze table t1 persistent for all; +Table Op Msg_type Msg_text +test.t1 analyze status Engine-independent statistics collected +test.t1 analyze status OK +explain format=json select * from t1 where a between 2 and 5; +EXPLAIN +{ + "query_block": { + "select_id": 1, + "cost": 0.027083745, + "nested_loop": [ + { + "table": { + "table_name": "t1", + "access_type": "ALL", + "loops": 1, + "rows": 109, + "cost": 0.027083745, + "filtered": 3.669724703, + "attached_condition": "t1.a between 2 and 5" + } + } + ] + } +} +explain format=json select * from t1 where a between 12 and 15; +EXPLAIN +{ + "query_block": { + "select_id": 1, + "cost": 0.027083745, + "nested_loop": [ + { + "table": { + "table_name": "t1", + "access_type": "ALL", + "loops": 1, + "rows": 109, + "cost": 0.027083745, + "filtered": 33.02752304, + "attached_condition": "t1.a between 12 and 15" + } + } + ] + } +} +flush tables; +set @@optimizer_use_condition_selectivity=3; +explain format=json select * from t1 where a between 2 and 5; +EXPLAIN +{ + "query_block": { + "select_id": 1, + "cost": 0.027083745, + "nested_loop": [ + { + "table": { + "table_name": "t1", + "access_type": "ALL", + "loops": 1, + "rows": 109, + "cost": 0.027083745, + "filtered": 15.78947353, + "attached_condition": "t1.a between 2 and 5" + } + } + ] + } +} +set @@optimizer_use_condition_selectivity=4; +explain format=json select * from t1 where a between 2 and 5; +EXPLAIN +{ + "query_block": { + "select_id": 1, + "cost": 0.027083745, + "nested_loop": [ + { + "table": { + "table_name": "t1", + "access_type": "ALL", + "loops": 1, + "rows": 109, + "cost": 0.027083745, + "filtered": 3.669724703, + "attached_condition": "t1.a between 2 and 5" + } + } + ] + } +} +drop table t1; +set @@optimizer_use_condition_selectivity=default; +# +# End of 10.6 tests +# diff --git a/mysql-test/main/stat_tables_flush.test b/mysql-test/main/stat_tables_flush.test new file mode 100644 index 00000000000..4c916f47ad7 --- /dev/null +++ b/mysql-test/main/stat_tables_flush.test @@ -0,0 +1,72 @@ +--source include/have_sequence.inc + +--echo # +--echo # Check that ANALYZE TABLE is remembered by MyISAM and Aria +--echo # + +create table t1 (a int) engine=myisam; +insert into t1 select seq from seq_0_to_99; +analyze table t1 persistent for all; +flush tables; +analyze table t1 persistent for all; +update t1 set a=100 where a=1; +analyze table t1 persistent for all; +update t1 set a=100 where a=2; +flush tables; +analyze table t1 persistent for all; + +--echo # Aria transactional=0 +ALTER TABLE t1 ENGINE=aria transactional=0; +analyze table t1 persistent for all; +update t1 set a=100 where a=10; +analyze table t1 persistent for all; +analyze table t1 persistent for all; +flush tables; +analyze table t1 persistent for all; +update t1 set a=100 where a=11; +analyze table t1 persistent for all; +update t1 set a=100 where a=12; +flush tables; +analyze table t1 persistent for all; + +--echo # Aria transactional=1 + +ALTER TABLE t1 ENGINE=aria transactional=1; +analyze table t1 persistent for all; +update t1 set a=100 where a=20; +analyze table t1 persistent for all; +analyze table t1 persistent for all; +flush tables; +analyze table t1 persistent for all; +update t1 set a=100 where a=21; +analyze table t1 persistent for all; +update t1 set a=100 where a=22; +flush tables; +analyze table t1 persistent for all; +drop table t1; + +--echo # +--echo # Test that histograms are read after flush +--echo # + +create table t1 (a int); +insert into t1 select seq from seq_1_to_10; + +insert into t1 select A.seq from seq_10_to_20 A, seq_1_to_9 B; +analyze table t1 persistent for all; + +explain format=json select * from t1 where a between 2 and 5; +explain format=json select * from t1 where a between 12 and 15; + +flush tables; +set @@optimizer_use_condition_selectivity=3; +explain format=json select * from t1 where a between 2 and 5; +set @@optimizer_use_condition_selectivity=4; +explain format=json select * from t1 where a between 2 and 5; + +drop table t1; +set @@optimizer_use_condition_selectivity=default; + +--echo # +--echo # End of 10.6 tests +--echo # diff --git a/mysql-test/main/stat_tables_innodb.result b/mysql-test/main/stat_tables_innodb.result index c90e99a9bbf..a7901c994b1 100644 --- a/mysql-test/main/stat_tables_innodb.result +++ b/mysql-test/main/stat_tables_innodb.result @@ -594,14 +594,14 @@ test.t1 analyze Warning Engine-independent statistics are not collected for colu test.t1 analyze status OK SELECT * FROM mysql.column_stats; db_name table_name column_name min_value max_value nulls_ratio avg_length avg_frequency hist_size hist_type histogram -test t1 pk 1 2 0.0000 4.0000 1.0000 0 NULL NULL +test t1 pk 1 2 0.0000 4.0000 1.0000 NULL NULL NULL DELETE FROM mysql.column_stats WHERE db_name='test' AND table_name='t1' AND column_name='t'; INSERT INTO mysql.column_stats VALUES ('test','t1','t','bar','foo', 0.0, 3.0, 1.0, 0, NULL, NULL); SELECT * FROM mysql.column_stats; db_name table_name column_name min_value max_value nulls_ratio avg_length avg_frequency hist_size hist_type histogram -test t1 pk 1 2 0.0000 4.0000 1.0000 0 NULL NULL +test t1 pk 1 2 0.0000 4.0000 1.0000 NULL NULL NULL test t1 t bar foo 0.0000 3.0000 1.0000 0 NULL NULL SELECT pk FROM t1; pk @@ -625,7 +625,7 @@ pk c 2 bar SELECT * FROM mysql.column_stats; db_name table_name column_name min_value max_value nulls_ratio avg_length avg_frequency hist_size hist_type histogram -test t1 pk 1 2 0.0000 4.0000 1.0000 0 NULL NULL +test t1 pk 1 2 0.0000 4.0000 1.0000 NULL NULL NULL test t1 c bar foo 0.0000 3.0000 1.0000 0 NULL NULL CREATE OR REPLACE TABLE t1 (pk int PRIMARY KEY, a char(7)); SELECT * FROM t1; @@ -955,7 +955,85 @@ id select_type table type possible_keys key key_len ref rows r_rows filtered r_f 1 SIMPLE t1 ALL NULL NULL NULL NULL 10 10.00 2.78 10.00 Using where drop table t1; set @@global.histogram_size=@save_histogram_size; +# # End of 10.4 tests +# +# +# MDEV-29693 ANALYZE TABLE still flushes table definition cache +# when engine-independent statistics is used +# +create table t1 (a int); +insert into t1 select seq from seq_0_to_99; +analyze table t1 persistent for all; +Table Op Msg_type Msg_text +test.t1 analyze status Engine-independent statistics collected +test.t1 analyze status OK +analyze table t1 persistent for all; +Table Op Msg_type Msg_text +test.t1 analyze status Engine-independent statistics collected +test.t1 analyze status OK +explain extended select count(*) from t1 where a < 50; +id select_type table type possible_keys key key_len ref rows filtered Extra +1 SIMPLE t1 ALL NULL NULL NULL NULL 100 50.51 Using where +Warnings: +Note 1003 select count(0) AS `count(*)` from `test`.`t1` where `test`.`t1`.`a` < 50 +connect con1, localhost, root,,; +connection con1; +explain extended select count(*) from t1 where a < 50; +id select_type table type possible_keys key key_len ref rows filtered Extra +1 SIMPLE t1 ALL NULL NULL NULL NULL 100 50.51 Using where +Warnings: +Note 1003 select count(0) AS `count(*)` from `test`.`t1` where `test`.`t1`.`a` < 50 +connection default; +update t1 set a= a +100; +# Explain shows outdated statistics: +explain extended select count(*) from t1 where a < 50; +id select_type table type possible_keys key key_len ref rows filtered Extra +1 SIMPLE t1 ALL NULL NULL NULL NULL 100 50.51 Using where +Warnings: +Note 1003 select count(0) AS `count(*)` from `test`.`t1` where `test`.`t1`.`a` < 50 +connection con1; +explain extended select count(*) from t1 where a < 50; +id select_type table type possible_keys key key_len ref rows filtered Extra +1 SIMPLE t1 ALL NULL NULL NULL NULL 100 50.51 Using where +Warnings: +Note 1003 select count(0) AS `count(*)` from `test`.`t1` where `test`.`t1`.`a` < 50 +connection default; +analyze table t1 persistent for all; +Table Op Msg_type Msg_text +test.t1 analyze status Engine-independent statistics collected +test.t1 analyze status OK +# Now explain shows updated statistics: +explain extended select count(*) from t1 where a < 50; +id select_type table type possible_keys key key_len ref rows filtered Extra +1 SIMPLE t1 ALL NULL NULL NULL NULL 100 1.00 Using where +Warnings: +Note 1003 select count(0) AS `count(*)` from `test`.`t1` where `test`.`t1`.`a` < 50 +connection con1; +explain extended select count(*) from t1 where a < 50; +id select_type table type possible_keys key key_len ref rows filtered Extra +1 SIMPLE t1 ALL NULL NULL NULL NULL 100 1.00 Using where +Warnings: +Note 1003 select count(0) AS `count(*)` from `test`.`t1` where `test`.`t1`.`a` < 50 +connection con1; +# Run update and analyze in con1: +update t1 set a= a - 150; +analyze table t1 persistent for all; +Table Op Msg_type Msg_text +test.t1 analyze status Engine-independent statistics collected +test.t1 analyze status OK +connection default; +# Explain shows updated statistics: +explain extended select count(*) from t1 where a < 50; +id select_type table type possible_keys key key_len ref rows filtered Extra +1 SIMPLE t1 ALL NULL NULL NULL NULL 100 100.00 Using where +Warnings: +Note 1003 select count(0) AS `count(*)` from `test`.`t1` where `test`.`t1`.`a` < 50 +disconnect con1; +drop table t1; +# +# End of 10.6 tests +# set global innodb_stats_persistent= @innodb_stats_persistent_save; set global innodb_stats_persistent_sample_pages= @innodb_stats_persistent_sample_pages_save; diff --git a/mysql-test/main/stat_tables_missing.result b/mysql-test/main/stat_tables_missing.result index 3f8f9e982ae..f7a1fcfbb90 100644 --- a/mysql-test/main/stat_tables_missing.result +++ b/mysql-test/main/stat_tables_missing.result @@ -2,6 +2,9 @@ create table t1 (a int); alter table mysql.column_stats rename to mysql.column_stats1; flush tables; alter table t1 change a b varchar(100); +Warnings: +Warning 1177 Got error 1146 when trying to open statistics table `table_stats` for updating statistics +Warning 1177 Got error 1146 when trying to open statistics table `table_stats` for updating statistics show create table t1; Table Create Table t1 CREATE TABLE `t1` ( diff --git a/mysql-test/main/statistics.result b/mysql-test/main/statistics.result index 3aa9fd1d306..f5ea0bf92e0 100644 --- a/mysql-test/main/statistics.result +++ b/mysql-test/main/statistics.result @@ -72,7 +72,7 @@ db_name table_name cardinality test t1 40 SELECT * FROM mysql.column_stats; db_name table_name column_name min_value max_value nulls_ratio avg_length avg_frequency hist_size hist_type histogram -test t1 a 0 49 0.0000 4.0000 1.0000 0 NULL NULL +test t1 a 0 49 0.0000 4.0000 1.0000 NULL NULL NULL test t1 b vvvvvvvvvvvvv zzzzzzzzzzzzzzzzzz 0.2000 17.1250 6.4000 0 NULL NULL test t1 c aaaa dddddddd 0.1250 6.6571 7.0000 0 NULL NULL test t1 d 1989-03-12 1999-07-23 0.1500 3.0000 8.5000 0 NULL NULL @@ -95,7 +95,7 @@ COUNT(*) SELECT * FROM mysql.column_stats WHERE db_name='test' AND table_name='t1' AND column_name='a'; db_name table_name column_name min_value max_value nulls_ratio avg_length avg_frequency hist_size hist_type histogram -test t1 a 0 49 0.0000 4.0000 1.0000 0 NULL NULL +test t1 a 0 49 0.0000 4.0000 1.0000 NULL NULL NULL SELECT MIN(t1.a), MAX(t1.a), (SELECT COUNT(*) FROM t1 WHERE t1.b IS NULL) / (SELECT COUNT(*) FROM t1) AS "NULLS_RATIO(t1.a)", @@ -226,7 +226,7 @@ hist_size, hist_type, decode_histogram(hist_type,histogram) FROM mysql.column_stats ORDER BY db_name, table_name, column_name; db_name table_name column_name min_value max_value nulls_ratio avg_frequency hist_size hist_type decode_histogram(hist_type,histogram) -test t1 a 0 49 0.0000 1.0000 4 SINGLE_PREC_HB 0.180,0.204,0.247,0.184,0.184 +test t1 a 0 49 0.0000 1.0000 NULL NULL NULL test t1 b vvvvvvvvvvvvv zzzzzzzzzzzzzzzzzz 0.2000 6.4000 4 SINGLE_PREC_HB 0.000,0.247,0.502,0.251,0.000 test t1 c aaaa dddddddd 0.1250 7.0000 4 SINGLE_PREC_HB 0.000,0.333,0.333,0.333,0.000 test t1 d 1989-03-12 1999-07-23 0.1500 8.5000 4 SINGLE_PREC_HB 0.000,0.098,0.000,0.902,0.000 @@ -246,7 +246,7 @@ hist_size, hist_type, decode_histogram(hist_type,histogram) FROM mysql.column_stats ORDER BY db_name, table_name, column_name; db_name table_name column_name min_value max_value nulls_ratio avg_frequency hist_size hist_type decode_histogram(hist_type,histogram) -test t1 a 0 49 0.0000 1.0000 8 DOUBLE_PREC_HB 0.18367,0.20407,0.24489,0.18367,0.18369 +test t1 a 0 49 0.0000 1.0000 NULL NULL NULL test t1 b vvvvvvvvvvvvv zzzzzzzzzzzzzzzzzz 0.2000 6.4000 8 DOUBLE_PREC_HB 0.00000,0.24999,0.50001,0.25000,0.00000 test t1 c aaaa dddddddd 0.1250 7.0000 8 DOUBLE_PREC_HB 0.00000,0.33333,0.33333,0.33333,0.00000 test t1 d 1989-03-12 1999-07-23 0.1500 8.5000 8 DOUBLE_PREC_HB 0.00000,0.10161,0.00000,0.89839,0.00000 @@ -293,13 +293,13 @@ test t1 40 test t3 17 SELECT * FROM mysql.column_stats; db_name table_name column_name min_value max_value nulls_ratio avg_length avg_frequency hist_size hist_type histogram -test t1 a 0 49 0.0000 4.0000 1.0000 0 NULL NULL +test t1 a 0 49 0.0000 4.0000 1.0000 NULL NULL NULL test t1 b vvvvvvvvvvvvv zzzzzzzzzzzzzzzzzz 0.2000 17.1250 6.4000 0 NULL NULL test t1 c aaaa dddddddd 0.1250 6.6571 7.0000 0 NULL NULL test t1 d 1989-03-12 1999-07-23 0.1500 3.0000 8.5000 0 NULL NULL test t1 e 0.01 0.112 0.2250 8.0000 6.2000 0 NULL NULL test t1 f 1 5 0.2000 1.0000 6.4000 0 NULL NULL -test t3 a 0 38 0.0000 4.0000 1.0000 0 NULL NULL +test t3 a 0 38 0.0000 4.0000 1.0000 NULL NULL NULL test t3 b vvvvvvvvvvvvv zzzzzzzzzzzzzzzzzz 0.1765 18.0714 2.8000 0 NULL NULL test t3 c aaaa dddddddd 0.1176 6.4000 3.7500 0 NULL NULL SELECT * FROM mysql.index_stats; @@ -322,13 +322,13 @@ test s1 40 test t3 17 SELECT * FROM mysql.column_stats; db_name table_name column_name min_value max_value nulls_ratio avg_length avg_frequency hist_size hist_type histogram -test s1 a 0 49 0.0000 4.0000 1.0000 0 NULL NULL +test s1 a 0 49 0.0000 4.0000 1.0000 NULL NULL NULL test s1 b vvvvvvvvvvvvv zzzzzzzzzzzzzzzzzz 0.2000 17.1250 6.4000 0 NULL NULL test s1 c aaaa dddddddd 0.1250 6.6571 7.0000 0 NULL NULL test s1 d 1989-03-12 1999-07-23 0.1500 3.0000 8.5000 0 NULL NULL test s1 e 0.01 0.112 0.2250 8.0000 6.2000 0 NULL NULL test s1 f 1 5 0.2000 1.0000 6.4000 0 NULL NULL -test t3 a 0 38 0.0000 4.0000 1.0000 0 NULL NULL +test t3 a 0 38 0.0000 4.0000 1.0000 NULL NULL NULL test t3 b vvvvvvvvvvvvv zzzzzzzzzzzzzzzzzz 0.1765 18.0714 2.8000 0 NULL NULL test t3 c aaaa dddddddd 0.1176 6.4000 3.7500 0 NULL NULL SELECT * FROM mysql.index_stats; @@ -351,13 +351,13 @@ test t1 40 test t3 17 SELECT * FROM mysql.column_stats; db_name table_name column_name min_value max_value nulls_ratio avg_length avg_frequency hist_size hist_type histogram -test t1 a 0 49 0.0000 4.0000 1.0000 0 NULL NULL +test t1 a 0 49 0.0000 4.0000 1.0000 NULL NULL NULL test t1 b vvvvvvvvvvvvv zzzzzzzzzzzzzzzzzz 0.2000 17.1250 6.4000 0 NULL NULL test t1 c aaaa dddddddd 0.1250 6.6571 7.0000 0 NULL NULL test t1 d 1989-03-12 1999-07-23 0.1500 3.0000 8.5000 0 NULL NULL test t1 e 0.01 0.112 0.2250 8.0000 6.2000 0 NULL NULL test t1 f 1 5 0.2000 1.0000 6.4000 0 NULL NULL -test t3 a 0 38 0.0000 4.0000 1.0000 0 NULL NULL +test t3 a 0 38 0.0000 4.0000 1.0000 NULL NULL NULL test t3 b vvvvvvvvvvvvv zzzzzzzzzzzzzzzzzz 0.1765 18.0714 2.8000 0 NULL NULL test t3 c aaaa dddddddd 0.1176 6.4000 3.7500 0 NULL NULL SELECT * FROM mysql.index_stats; @@ -379,7 +379,7 @@ db_name table_name cardinality test t1 40 SELECT * FROM mysql.column_stats; db_name table_name column_name min_value max_value nulls_ratio avg_length avg_frequency hist_size hist_type histogram -test t1 a 0 49 0.0000 4.0000 1.0000 0 NULL NULL +test t1 a 0 49 0.0000 4.0000 1.0000 NULL NULL NULL test t1 b vvvvvvvvvvvvv zzzzzzzzzzzzzzzzzz 0.2000 17.1250 6.4000 0 NULL NULL test t1 c aaaa dddddddd 0.1250 6.6571 7.0000 0 NULL NULL test t1 d 1989-03-12 1999-07-23 0.1500 3.0000 8.5000 0 NULL NULL @@ -420,7 +420,7 @@ t1 CREATE TABLE `t1` ( ) ENGINE=MyISAM DEFAULT CHARSET=latin1 COLLATE=latin1_swedish_ci SELECT * FROM mysql.column_stats; db_name table_name column_name min_value max_value nulls_ratio avg_length avg_frequency hist_size hist_type histogram -test t1 a 0 49 0.0000 4.0000 1.0000 0 NULL NULL +test t1 a 0 49 0.0000 4.0000 1.0000 NULL NULL NULL test t1 c aaaa dddddddd 0.1250 6.6571 7.0000 0 NULL NULL test t1 d 1989-03-12 1999-07-23 0.1500 3.0000 8.5000 0 NULL NULL test t1 f 1 5 0.2000 1.0000 6.4000 0 NULL NULL @@ -445,7 +445,7 @@ t1 CREATE TABLE `t1` ( ) ENGINE=MyISAM DEFAULT CHARSET=latin1 COLLATE=latin1_swedish_ci SELECT * FROM mysql.column_stats; db_name table_name column_name min_value max_value nulls_ratio avg_length avg_frequency hist_size hist_type histogram -test t1 a 0 49 0.0000 4.0000 1.0000 0 NULL NULL +test t1 a 0 49 0.0000 4.0000 1.0000 NULL NULL NULL test t1 b vvvvvvvvvvvvv zzzzzzzzzzzzzzzzzz 0.2000 17.1250 6.4000 0 NULL NULL test t1 c aaaa dddddddd 0.1250 6.6571 7.0000 0 NULL NULL test t1 d 1989-03-12 1999-07-23 0.1500 3.0000 8.5000 0 NULL NULL @@ -472,7 +472,7 @@ db_name table_name cardinality test s1 40 SELECT * FROM mysql.column_stats; db_name table_name column_name min_value max_value nulls_ratio avg_length avg_frequency hist_size hist_type histogram -test s1 a 0 49 0.0000 4.0000 1.0000 0 NULL NULL +test s1 a 0 49 0.0000 4.0000 1.0000 NULL NULL NULL test s1 c aaaa dddddddd 0.1250 6.6571 7.0000 0 NULL NULL test s1 d 1989-03-12 1999-07-23 0.1500 3.0000 8.5000 0 NULL NULL test s1 e 0.01 0.112 0.2250 8.0000 6.2000 0 NULL NULL @@ -510,7 +510,7 @@ db_name table_name cardinality test t1 40 SELECT * FROM mysql.column_stats; db_name table_name column_name min_value max_value nulls_ratio avg_length avg_frequency hist_size hist_type histogram -test t1 a 0 49 0.0000 4.0000 1.0000 0 NULL NULL +test t1 a 0 49 0.0000 4.0000 1.0000 NULL NULL NULL test t1 b vvvvvvvvvvvvv zzzzzzzzzzzzzzzzzz 0.2000 17.1250 6.4000 0 NULL NULL test t1 c aaaa dddddddd 0.1250 6.6571 7.0000 0 NULL NULL test t1 d 1989-03-12 1999-07-23 0.1500 3.0000 8.5000 0 NULL NULL @@ -545,7 +545,7 @@ t1 CREATE TABLE `t1` ( ) ENGINE=MyISAM DEFAULT CHARSET=latin1 COLLATE=latin1_swedish_ci SELECT * FROM mysql.column_stats; db_name table_name column_name min_value max_value nulls_ratio avg_length avg_frequency hist_size hist_type histogram -test t1 a 0 49 0.0000 4.0000 1.0000 0 NULL NULL +test t1 a 0 49 0.0000 4.0000 1.0000 NULL NULL NULL test t1 c aaaa dddddddd 0.1250 6.6571 7.0000 0 NULL NULL test t1 d 1989-03-12 1999-07-23 0.1500 3.0000 8.5000 0 NULL NULL test t1 e 0.01 0.112 0.2250 8.0000 6.2000 0 NULL NULL @@ -556,6 +556,13 @@ test t1 PRIMARY 1 1.0000 test t1 idx2 1 7.0000 test t1 idx2 2 2.3846 test t1 idx3 1 8.5000 +ANALYZE TABLE t1 PERSISTENT FOR COLUMNS(x) INDEXES(); +Table Op Msg_type Msg_text +test.t1 analyze status Engine-independent statistics collected +test.t1 analyze status OK +SELECT * FROM mysql.column_stats where column_name="x"; +db_name table_name column_name min_value max_value nulls_ratio avg_length avg_frequency hist_size hist_type histogram +test t1 x vvvvvvvvvvvvv zzzzzzzzzzzzzzzzzz 0.2000 17.1250 6.4000 0 NULL NULL ALTER TABLE t1 CHANGE COLUMN x b varchar(32); SHOW CREATE TABLE t1; Table Create Table @@ -574,7 +581,7 @@ t1 CREATE TABLE `t1` ( ) ENGINE=MyISAM DEFAULT CHARSET=latin1 COLLATE=latin1_swedish_ci SELECT * FROM mysql.column_stats; db_name table_name column_name min_value max_value nulls_ratio avg_length avg_frequency hist_size hist_type histogram -test t1 a 0 49 0.0000 4.0000 1.0000 0 NULL NULL +test t1 a 0 49 0.0000 4.0000 1.0000 NULL NULL NULL test t1 c aaaa dddddddd 0.1250 6.6571 7.0000 0 NULL NULL test t1 d 1989-03-12 1999-07-23 0.1500 3.0000 8.5000 0 NULL NULL test t1 e 0.01 0.112 0.2250 8.0000 6.2000 0 NULL NULL @@ -591,7 +598,7 @@ test.t1 analyze status Engine-independent statistics collected test.t1 analyze status OK SELECT * FROM mysql.column_stats; db_name table_name column_name min_value max_value nulls_ratio avg_length avg_frequency hist_size hist_type histogram -test t1 a 0 49 0.0000 4.0000 1.0000 0 NULL NULL +test t1 a 0 49 0.0000 4.0000 1.0000 NULL NULL NULL test t1 b vvvvvvvvvvvvv zzzzzzzzzzzzzzzzzz 0.2000 17.1250 6.4000 0 NULL NULL test t1 c aaaa dddddddd 0.1250 6.6571 7.0000 0 NULL NULL test t1 d 1989-03-12 1999-07-23 0.1500 3.0000 8.5000 0 NULL NULL @@ -632,7 +639,7 @@ t1 CREATE TABLE `t1` ( ) ENGINE=MyISAM DEFAULT CHARSET=latin1 COLLATE=latin1_swedish_ci SELECT * FROM mysql.column_stats; db_name table_name column_name min_value max_value nulls_ratio avg_length avg_frequency hist_size hist_type histogram -test t1 a 0 49 0.0000 4.0000 1.0000 0 NULL NULL +test t1 a 0 49 0.0000 4.0000 1.0000 NULL NULL NULL test t1 c aaaa dddddddd 0.1250 6.6571 7.0000 0 NULL NULL test t1 d 1989-03-12 1999-07-23 0.1500 3.0000 8.5000 0 NULL NULL test t1 e 0.01 0.112 0.2250 8.0000 6.2000 0 NULL NULL @@ -661,7 +668,7 @@ t1 CREATE TABLE `t1` ( ) ENGINE=MyISAM DEFAULT CHARSET=latin1 COLLATE=latin1_swedish_ci SELECT * FROM mysql.column_stats; db_name table_name column_name min_value max_value nulls_ratio avg_length avg_frequency hist_size hist_type histogram -test t1 a 0 49 0.0000 4.0000 1.0000 0 NULL NULL +test t1 a 0 49 0.0000 4.0000 1.0000 NULL NULL NULL test t1 c aaaa dddddddd 0.1250 6.6571 7.0000 0 NULL NULL test t1 d 1989-03-12 1999-07-23 0.1500 3.0000 8.5000 0 NULL NULL test t1 e 0.01 0.112 0.2250 8.0000 6.2000 0 NULL NULL @@ -672,15 +679,15 @@ test t1 PRIMARY 1 1.0000 test t1 idx2 1 7.0000 test t1 idx2 2 2.3846 test t1 idx3 1 8.5000 -LOAD DATA INFILE 'MYSQLTEST_VARDIR/tmp/save_column_stats' - INTO TABLE mysql.column_stats +LOAD DATA INFILE 'MYSQLTEST_VARDIR/tmp/save_column_stats' IGNORE +INTO TABLE mysql.column_stats FIELDS TERMINATED BY ',' OPTIONALLY ENCLOSED BY '"' LINES TERMINATED BY '\n'; LOAD DATA INFILE 'MYSQLTEST_VARDIR/tmp/save_index_stats' INTO TABLE mysql.index_stats FIELDS TERMINATED BY ',' OPTIONALLY ENCLOSED BY '"' LINES TERMINATED BY '\n'; SELECT * FROM mysql.column_stats; db_name table_name column_name min_value max_value nulls_ratio avg_length avg_frequency hist_size hist_type histogram -test t1 a 0 49 0.0000 4.0000 1.0000 0 NULL NULL +test t1 a 0 49 0.0000 4.0000 1.0000 NULL NULL NULL test t1 b vvvvvvvvvvvvv zzzzzzzzzzzzzzzzzz 0.2000 17.1250 6.4000 0 NULL NULL test t1 c aaaa dddddddd 0.1250 6.6571 7.0000 0 NULL NULL test t1 d 1989-03-12 1999-07-23 0.1500 3.0000 8.5000 0 NULL NULL @@ -714,7 +721,7 @@ t1 CREATE TABLE `t1` ( ) ENGINE=MyISAM DEFAULT CHARSET=latin1 COLLATE=latin1_swedish_ci SELECT * FROM mysql.column_stats; db_name table_name column_name min_value max_value nulls_ratio avg_length avg_frequency hist_size hist_type histogram -test t1 a 0 49 0.0000 4.0000 1.0000 0 NULL NULL +test t1 a 0 49 0.0000 4.0000 1.0000 NULL NULL NULL test t1 c aaaa dddddddd 0.1250 6.6571 7.0000 0 NULL NULL test t1 d 1989-03-12 1999-07-23 0.1500 3.0000 8.5000 0 NULL NULL test t1 e 0.01 0.112 0.2250 8.0000 6.2000 0 NULL NULL @@ -777,7 +784,7 @@ t1 CREATE TABLE `t1` ( ) ENGINE=MyISAM DEFAULT CHARSET=latin1 COLLATE=latin1_swedish_ci SELECT * FROM mysql.column_stats; db_name table_name column_name min_value max_value nulls_ratio avg_length avg_frequency hist_size hist_type histogram -test t1 a 0 49 0.0000 4.0000 1.0000 0 NULL NULL +test t1 a 0 49 0.0000 4.0000 1.0000 NULL NULL NULL test t1 c aaaa dddddddd 0.1250 6.6571 7.0000 0 NULL NULL test t1 d 1989-03-12 1999-07-23 0.1500 3.0000 8.5000 0 NULL NULL test t1 e 0.01 0.112 0.2250 8.0000 6.2000 0 NULL NULL @@ -792,7 +799,7 @@ test.t1 analyze status Engine-independent statistics collected test.t1 analyze status OK SELECT * FROM mysql.column_stats; db_name table_name column_name min_value max_value nulls_ratio avg_length avg_frequency hist_size hist_type histogram -test t1 a 0 49 0.0000 4.0000 1.0000 0 NULL NULL +test t1 a 0 49 0.0000 4.0000 1.0000 NULL NULL NULL test t1 b NULL NULL 1.0000 NULL NULL 0 NULL NULL test t1 c aaaa dddddddd 0.1250 6.6571 7.0000 0 NULL NULL test t1 d 1989-03-12 1999-07-23 0.1500 3.0000 8.5000 0 NULL NULL @@ -816,7 +823,7 @@ test.t1 analyze status Engine-independent statistics collected test.t1 analyze status OK SELECT * FROM mysql.column_stats; db_name table_name column_name min_value max_value nulls_ratio avg_length avg_frequency hist_size hist_type histogram -test t1 a 0 49 0.0000 4.0000 1.0000 0 NULL NULL +test t1 a 0 49 0.0000 4.0000 1.0000 NULL NULL NULL test t1 b vvvvvvvvvvvvv zzzzzzzzzzzzzzzzzz 0.2000 17.1250 6.4000 0 NULL NULL test t1 c aaaa dddddddd 0.1250 6.6571 7.0000 0 NULL NULL test t1 d 1989-03-12 1999-07-23 0.1500 3.0000 8.5000 0 NULL NULL @@ -848,7 +855,7 @@ t1 CREATE TABLE `t1` ( ) ENGINE=MyISAM DEFAULT CHARSET=latin1 COLLATE=latin1_swedish_ci SELECT * FROM mysql.column_stats; db_name table_name column_name min_value max_value nulls_ratio avg_length avg_frequency hist_size hist_type histogram -test t1 a 0 49 0.0000 4.0000 1.0000 0 NULL NULL +test t1 a 0 49 0.0000 4.0000 1.0000 NULL NULL NULL test t1 c aaaa dddddddd 0.1250 6.6571 7.0000 0 NULL NULL test t1 d 1989-03-12 1999-07-23 0.1500 3.0000 8.5000 0 NULL NULL test t1 e 0.01 0.112 0.2250 8.0000 6.2000 0 NULL NULL @@ -878,7 +885,7 @@ t1 CREATE TABLE `t1` ( ) ENGINE=MyISAM DEFAULT CHARSET=latin1 COLLATE=latin1_swedish_ci SELECT * FROM mysql.column_stats; db_name table_name column_name min_value max_value nulls_ratio avg_length avg_frequency hist_size hist_type histogram -test t1 a 0 49 0.0000 4.0000 1.0000 0 NULL NULL +test t1 a 0 49 0.0000 4.0000 1.0000 NULL NULL NULL test t1 c aaaa dddddddd 0.1250 6.6571 7.0000 0 NULL NULL test t1 d 1989-03-12 1999-07-23 0.1500 3.0000 8.5000 0 NULL NULL test t1 e 0.01 0.112 0.2250 8.0000 6.2000 0 NULL NULL @@ -893,7 +900,7 @@ test.t1 analyze status Engine-independent statistics collected test.t1 analyze status OK SELECT * FROM mysql.column_stats; db_name table_name column_name min_value max_value nulls_ratio avg_length avg_frequency hist_size hist_type histogram -test t1 a 0 49 0.0000 4.0000 1.0000 0 NULL NULL +test t1 a 0 49 0.0000 4.0000 1.0000 NULL NULL NULL test t1 b vvvvvvvvvvvvv zzzzzzzzzzzzzzzzzz 0.2000 17.1250 6.4000 0 NULL NULL test t1 c aaaa dddddddd 0.1250 6.6571 7.0000 0 NULL NULL test t1 d 1989-03-12 1999-07-23 0.1500 3.0000 8.5000 0 NULL NULL @@ -975,7 +982,7 @@ db_name table_name cardinality test t1 40 SELECT * FROM mysql.column_stats; db_name table_name column_name min_value max_value nulls_ratio avg_length avg_frequency hist_size hist_type histogram -test t1 a 0 49 0.0000 4.0000 1.0000 0 NULL NULL +test t1 a 0 49 0.0000 4.0000 1.0000 NULL NULL NULL test t1 b vvvvvvvvvvvvv zzzzzzzzzzzzzzzzzz 0.2000 17.1250 6.4000 0 NULL NULL test t1 c aaaa dddddddd 0.1250 6.6571 7.0000 0 NULL NULL test t1 d 1989-03-12 1999-07-23 0.1500 3.0000 8.5000 0 NULL NULL @@ -1006,8 +1013,8 @@ test t1 40 test t2 40 SELECT * FROM mysql.column_stats ORDER BY column_name, table_name; db_name table_name column_name min_value max_value nulls_ratio avg_length avg_frequency hist_size hist_type histogram -test t1 a 0 49 0.0000 4.0000 1.0000 0 NULL NULL -test t2 a 0 49 0.0000 4.0000 1.0000 0 NULL NULL +test t1 a 0 49 0.0000 4.0000 1.0000 NULL NULL NULL +test t2 a 0 49 0.0000 4.0000 1.0000 NULL NULL NULL test t1 b vvvvvvvvvvvvv zzzzzzzzzzzzzzzzzz 0.2000 17.1250 6.4000 0 NULL NULL test t2 b vvvvvvvvvvvvv zzzzzzzzzzzzzzzzzz 0.2000 17.1250 6.4000 0 NULL NULL test t1 c aaaa dddddddd 0.1250 6.6571 7.0000 0 NULL NULL @@ -1051,7 +1058,7 @@ db_name table_name cardinality test t2 40 SELECT * FROM mysql.column_stats ORDER BY column_name; db_name table_name column_name min_value max_value nulls_ratio avg_length avg_frequency hist_size hist_type histogram -test t2 a 0 49 0.0000 4.0000 1.0000 0 NULL NULL +test t2 a 0 49 0.0000 4.0000 1.0000 NULL NULL NULL test t2 b vvvvvvvvvvvvv zzzzzzzzzzzzzzzzzz 0.2000 17.1250 6.4000 0 NULL NULL test t2 c aaaa dddddddd 0.1250 6.6571 7.0000 0 NULL NULL test t2 d 1989-03-12 1999-07-23 0.1500 3.0000 8.5000 0 NULL NULL @@ -1110,12 +1117,17 @@ test t2 idx4 1 6.2000 test t2 idx4 2 1.7222 test t2 idx4 3 1.1154 test t2 idx4 4 1.0000 +SELECT * FROM mysql.column_stats where column_name="b"; +db_name table_name column_name min_value max_value nulls_ratio avg_length avg_frequency hist_size hist_type histogram +test t2 b vvvvvvvvvvvvv zzzzzzzzzzzzzzzzzz 0.2000 17.1250 6.4000 0 NULL NULL ALTER TABLE t2 CHANGE COLUMN b b varchar(30); SELECT * FROM mysql.index_stats ORDER BY index_name, prefix_arity, table_name; db_name table_name index_name prefix_arity avg_frequency test t2 idx2 1 7.0000 test t2 idx2 2 2.3846 test t2 idx3 1 8.5000 +SELECT * FROM mysql.column_stats where column_name="b"; +db_name table_name column_name min_value max_value nulls_ratio avg_length avg_frequency hist_size hist_type histogram ANALYZE TABLE t2 PERSISTENT FOR COLUMNS ALL INDEXES ALL; Table Op Msg_type Msg_text test.t2 analyze status Engine-independent statistics collected @@ -1151,6 +1163,9 @@ test t2 idx4 1 6.2000 test t2 idx4 2 1.7222 test t2 idx4 3 1.1154 test t2 idx4 4 1.0000 +SELECT * FROM mysql.column_stats where column_name="b"; +db_name table_name column_name min_value max_value nulls_ratio avg_length avg_frequency hist_size hist_type histogram +test t2 b 0 zzzzzzzzzzzzzzzzzz 0.0000 13.9000 6.6667 0 NULL NULL ANALYZE TABLE t2 PERSISTENT FOR COLUMNS ALL INDEXES ALL; Table Op Msg_type Msg_text test.t2 analyze status Engine-independent statistics collected @@ -1224,7 +1239,7 @@ test.t1 analyze Warning Engine-independent statistics are not collected for colu test.t1 analyze status OK SELECT * FROM mysql.column_stats; db_name table_name column_name min_value max_value nulls_ratio avg_length avg_frequency hist_size hist_type histogram -test t1 a 0 49 0.0000 4.0000 1.0000 0 NULL NULL +test t1 a 0 49 0.0000 4.0000 1.0000 NULL NULL NULL test t1 c aaaa dddddddd 0.1250 6.6571 7.0000 0 NULL NULL test t1 d 1989-03-12 1999-07-23 0.1500 3.0000 8.5000 0 NULL NULL test t1 e 0.01 0.112 0.2250 8.0000 6.2000 0 NULL NULL @@ -1280,7 +1295,7 @@ db_name table_name cardinality test t1 40 SELECT * FROM mysql.column_stats; db_name table_name column_name min_value max_value nulls_ratio avg_length avg_frequency hist_size hist_type histogram -test t1 a 0 49 0.0000 4.0000 1.0000 0 NULL NULL +test t1 a 0 49 0.0000 4.0000 1.0000 NULL NULL NULL test t1 c aaaa dddddddd 0.1250 6.6571 7.0000 0 NULL NULL test t1 d 1989-03-12 1999-07-23 0.1500 3.0000 8.5000 0 NULL NULL test t1 e 0.01 0.112 0.2250 8.0000 6.2000 0 NULL NULL diff --git a/mysql-test/main/statistics.test b/mysql-test/main/statistics.test index 7faf35be9a5..c964bc2ec23 100644 --- a/mysql-test/main/statistics.test +++ b/mysql-test/main/statistics.test @@ -315,6 +315,10 @@ SELECT * FROM mysql.column_stats; --sorted_result SELECT * FROM mysql.index_stats; +# Add 'x' back that was deleted above +ANALYZE TABLE t1 PERSISTENT FOR COLUMNS(x) INDEXES(); +SELECT * FROM mysql.column_stats where column_name="x"; + ALTER TABLE t1 CHANGE COLUMN x b varchar(32); SHOW CREATE TABLE t1; --sorted_result @@ -357,7 +361,7 @@ SELECT * FROM mysql.index_stats; --replace_result $MYSQLTEST_VARDIR MYSQLTEST_VARDIR eval -LOAD DATA INFILE '$MYSQLTEST_VARDIR/tmp/save_column_stats' +LOAD DATA INFILE '$MYSQLTEST_VARDIR/tmp/save_column_stats' IGNORE INTO TABLE mysql.column_stats FIELDS TERMINATED BY ',' OPTIONALLY ENCLOSED BY '"' LINES TERMINATED BY '\n'; --replace_result $MYSQLTEST_VARDIR MYSQLTEST_VARDIR @@ -505,14 +509,17 @@ SELECT * FROM mysql.index_stats ORDER BY index_name, prefix_arity, table_name; ANALYZE TABLE t2 PERSISTENT FOR COLUMNS() INDEXES ALL; SELECT * FROM mysql.index_stats ORDER BY index_name, prefix_arity, table_name; +SELECT * FROM mysql.column_stats where column_name="b"; ALTER TABLE t2 CHANGE COLUMN b b varchar(30); SELECT * FROM mysql.index_stats ORDER BY index_name, prefix_arity, table_name; +SELECT * FROM mysql.column_stats where column_name="b"; ANALYZE TABLE t2 PERSISTENT FOR COLUMNS ALL INDEXES ALL; SELECT * FROM mysql.index_stats ORDER BY index_name, prefix_arity, table_name; ALTER TABLE t2 CHANGE COLUMN b b varchar(32); SELECT * FROM mysql.index_stats ORDER BY index_name, prefix_arity, table_name; +SELECT * FROM mysql.column_stats where column_name="b"; ANALYZE TABLE t2 PERSISTENT FOR COLUMNS ALL INDEXES ALL; SELECT * FROM mysql.index_stats ORDER BY index_name, prefix_arity, table_name; diff --git a/mysql-test/main/statistics_json.result b/mysql-test/main/statistics_json.result index 7b7cc86642c..0d1953e922b 100644 --- a/mysql-test/main/statistics_json.result +++ b/mysql-test/main/statistics_json.result @@ -78,7 +78,7 @@ db_name table_name cardinality test t1 40 SELECT * FROM mysql.column_stats; db_name table_name column_name min_value max_value nulls_ratio avg_length avg_frequency hist_size hist_type histogram -test t1 a 0 49 0.0000 4.0000 1.0000 0 NULL NULL +test t1 a 0 49 0.0000 4.0000 1.0000 NULL NULL NULL test t1 b vvvvvvvvvvvvv zzzzzzzzzzzzzzzzzz 0.2000 17.1250 6.4000 0 NULL NULL test t1 c aaaa dddddddd 0.1250 6.6571 7.0000 0 NULL NULL test t1 d 1989-03-12 1999-07-23 0.1500 3.0000 8.5000 0 NULL NULL @@ -101,7 +101,7 @@ COUNT(*) SELECT * FROM mysql.column_stats WHERE db_name='test' AND table_name='t1' AND column_name='a'; db_name table_name column_name min_value max_value nulls_ratio avg_length avg_frequency hist_size hist_type histogram -test t1 a 0 49 0.0000 4.0000 1.0000 0 NULL NULL +test t1 a 0 49 0.0000 4.0000 1.0000 NULL NULL NULL SELECT MIN(t1.a), MAX(t1.a), (SELECT COUNT(*) FROM t1 WHERE t1.b IS NULL) / (SELECT COUNT(*) FROM t1) AS "NULLS_RATIO(t1.a)", @@ -232,34 +232,7 @@ hist_size, hist_type, decode_histogram(hist_type,histogram) FROM mysql.column_stats ORDER BY db_name, table_name, column_name; db_name table_name column_name min_value max_value nulls_ratio avg_frequency hist_size hist_type decode_histogram(hist_type,histogram) -test t1 a 0 49 0.0000 1.0000 4 JSON_HB { - "target_histogram_size": 4, - "collected_at": "REPLACED", - "collected_by": "REPLACED", - "histogram_hb": [ - { - "start": "0", - "size": 0.275, - "ndv": 11 - }, - { - "start": "12", - "size": 0.275, - "ndv": 11 - }, - { - "start": "29", - "size": 0.275, - "ndv": 11 - }, - { - "start": "41", - "end": "49", - "size": 0.175, - "ndv": 7 - } - ] -} +test t1 a 0 49 0.0000 1.0000 NULL NULL NULL test t1 b vvvvvvvvvvvvv zzzzzzzzzzzzzzzzzz 0.2000 6.4000 4 JSON_HB { "target_histogram_size": 4, "collected_at": "REPLACED", @@ -409,49 +382,7 @@ hist_size, hist_type, decode_histogram(hist_type,histogram) FROM mysql.column_stats ORDER BY db_name, table_name, column_name; db_name table_name column_name min_value max_value nulls_ratio avg_frequency hist_size hist_type decode_histogram(hist_type,histogram) -test t1 a 0 49 0.0000 1.0000 7 JSON_HB { - "target_histogram_size": 8, - "collected_at": "REPLACED", - "collected_by": "REPLACED", - "histogram_hb": [ - { - "start": "0", - "size": 0.15, - "ndv": 6 - }, - { - "start": "7", - "size": 0.15, - "ndv": 6 - }, - { - "start": "14", - "size": 0.15, - "ndv": 6 - }, - { - "start": "22", - "size": 0.15, - "ndv": 6 - }, - { - "start": "31", - "size": 0.15, - "ndv": 6 - }, - { - "start": "38", - "size": 0.15, - "ndv": 6 - }, - { - "start": "44", - "end": "49", - "size": 0.1, - "ndv": 4 - } - ] -} +test t1 a 0 49 0.0000 1.0000 NULL NULL NULL test t1 b vvvvvvvvvvvvv zzzzzzzzzzzzzzzzzz 0.2000 6.4000 5 JSON_HB { "target_histogram_size": 8, "collected_at": "REPLACED", @@ -653,13 +584,13 @@ test t1 40 test t3 17 SELECT * FROM mysql.column_stats; db_name table_name column_name min_value max_value nulls_ratio avg_length avg_frequency hist_size hist_type histogram -test t1 a 0 49 0.0000 4.0000 1.0000 0 NULL NULL +test t1 a 0 49 0.0000 4.0000 1.0000 NULL NULL NULL test t1 b vvvvvvvvvvvvv zzzzzzzzzzzzzzzzzz 0.2000 17.1250 6.4000 0 NULL NULL test t1 c aaaa dddddddd 0.1250 6.6571 7.0000 0 NULL NULL test t1 d 1989-03-12 1999-07-23 0.1500 3.0000 8.5000 0 NULL NULL test t1 e 0.01 0.112 0.2250 8.0000 6.2000 0 NULL NULL test t1 f 1 5 0.2000 1.0000 6.4000 0 NULL NULL -test t3 a 0 38 0.0000 4.0000 1.0000 0 NULL NULL +test t3 a 0 38 0.0000 4.0000 1.0000 NULL NULL NULL test t3 b vvvvvvvvvvvvv zzzzzzzzzzzzzzzzzz 0.1765 18.0714 2.8000 0 NULL NULL test t3 c aaaa dddddddd 0.1176 6.4000 3.7500 0 NULL NULL SELECT * FROM mysql.index_stats; @@ -682,13 +613,13 @@ test s1 40 test t3 17 SELECT * FROM mysql.column_stats; db_name table_name column_name min_value max_value nulls_ratio avg_length avg_frequency hist_size hist_type histogram -test s1 a 0 49 0.0000 4.0000 1.0000 0 NULL NULL +test s1 a 0 49 0.0000 4.0000 1.0000 NULL NULL NULL test s1 b vvvvvvvvvvvvv zzzzzzzzzzzzzzzzzz 0.2000 17.1250 6.4000 0 NULL NULL test s1 c aaaa dddddddd 0.1250 6.6571 7.0000 0 NULL NULL test s1 d 1989-03-12 1999-07-23 0.1500 3.0000 8.5000 0 NULL NULL test s1 e 0.01 0.112 0.2250 8.0000 6.2000 0 NULL NULL test s1 f 1 5 0.2000 1.0000 6.4000 0 NULL NULL -test t3 a 0 38 0.0000 4.0000 1.0000 0 NULL NULL +test t3 a 0 38 0.0000 4.0000 1.0000 NULL NULL NULL test t3 b vvvvvvvvvvvvv zzzzzzzzzzzzzzzzzz 0.1765 18.0714 2.8000 0 NULL NULL test t3 c aaaa dddddddd 0.1176 6.4000 3.7500 0 NULL NULL SELECT * FROM mysql.index_stats; @@ -711,13 +642,13 @@ test t1 40 test t3 17 SELECT * FROM mysql.column_stats; db_name table_name column_name min_value max_value nulls_ratio avg_length avg_frequency hist_size hist_type histogram -test t1 a 0 49 0.0000 4.0000 1.0000 0 NULL NULL +test t1 a 0 49 0.0000 4.0000 1.0000 NULL NULL NULL test t1 b vvvvvvvvvvvvv zzzzzzzzzzzzzzzzzz 0.2000 17.1250 6.4000 0 NULL NULL test t1 c aaaa dddddddd 0.1250 6.6571 7.0000 0 NULL NULL test t1 d 1989-03-12 1999-07-23 0.1500 3.0000 8.5000 0 NULL NULL test t1 e 0.01 0.112 0.2250 8.0000 6.2000 0 NULL NULL test t1 f 1 5 0.2000 1.0000 6.4000 0 NULL NULL -test t3 a 0 38 0.0000 4.0000 1.0000 0 NULL NULL +test t3 a 0 38 0.0000 4.0000 1.0000 NULL NULL NULL test t3 b vvvvvvvvvvvvv zzzzzzzzzzzzzzzzzz 0.1765 18.0714 2.8000 0 NULL NULL test t3 c aaaa dddddddd 0.1176 6.4000 3.7500 0 NULL NULL SELECT * FROM mysql.index_stats; @@ -739,7 +670,7 @@ db_name table_name cardinality test t1 40 SELECT * FROM mysql.column_stats; db_name table_name column_name min_value max_value nulls_ratio avg_length avg_frequency hist_size hist_type histogram -test t1 a 0 49 0.0000 4.0000 1.0000 0 NULL NULL +test t1 a 0 49 0.0000 4.0000 1.0000 NULL NULL NULL test t1 b vvvvvvvvvvvvv zzzzzzzzzzzzzzzzzz 0.2000 17.1250 6.4000 0 NULL NULL test t1 c aaaa dddddddd 0.1250 6.6571 7.0000 0 NULL NULL test t1 d 1989-03-12 1999-07-23 0.1500 3.0000 8.5000 0 NULL NULL @@ -780,7 +711,7 @@ t1 CREATE TABLE `t1` ( ) ENGINE=MyISAM DEFAULT CHARSET=latin1 COLLATE=latin1_swedish_ci SELECT * FROM mysql.column_stats; db_name table_name column_name min_value max_value nulls_ratio avg_length avg_frequency hist_size hist_type histogram -test t1 a 0 49 0.0000 4.0000 1.0000 0 NULL NULL +test t1 a 0 49 0.0000 4.0000 1.0000 NULL NULL NULL test t1 c aaaa dddddddd 0.1250 6.6571 7.0000 0 NULL NULL test t1 d 1989-03-12 1999-07-23 0.1500 3.0000 8.5000 0 NULL NULL test t1 f 1 5 0.2000 1.0000 6.4000 0 NULL NULL @@ -805,7 +736,7 @@ t1 CREATE TABLE `t1` ( ) ENGINE=MyISAM DEFAULT CHARSET=latin1 COLLATE=latin1_swedish_ci SELECT * FROM mysql.column_stats; db_name table_name column_name min_value max_value nulls_ratio avg_length avg_frequency hist_size hist_type histogram -test t1 a 0 49 0.0000 4.0000 1.0000 0 NULL NULL +test t1 a 0 49 0.0000 4.0000 1.0000 NULL NULL NULL test t1 b vvvvvvvvvvvvv zzzzzzzzzzzzzzzzzz 0.2000 17.1250 6.4000 0 NULL NULL test t1 c aaaa dddddddd 0.1250 6.6571 7.0000 0 NULL NULL test t1 d 1989-03-12 1999-07-23 0.1500 3.0000 8.5000 0 NULL NULL @@ -832,7 +763,7 @@ db_name table_name cardinality test s1 40 SELECT * FROM mysql.column_stats; db_name table_name column_name min_value max_value nulls_ratio avg_length avg_frequency hist_size hist_type histogram -test s1 a 0 49 0.0000 4.0000 1.0000 0 NULL NULL +test s1 a 0 49 0.0000 4.0000 1.0000 NULL NULL NULL test s1 c aaaa dddddddd 0.1250 6.6571 7.0000 0 NULL NULL test s1 d 1989-03-12 1999-07-23 0.1500 3.0000 8.5000 0 NULL NULL test s1 e 0.01 0.112 0.2250 8.0000 6.2000 0 NULL NULL @@ -870,7 +801,7 @@ db_name table_name cardinality test t1 40 SELECT * FROM mysql.column_stats; db_name table_name column_name min_value max_value nulls_ratio avg_length avg_frequency hist_size hist_type histogram -test t1 a 0 49 0.0000 4.0000 1.0000 0 NULL NULL +test t1 a 0 49 0.0000 4.0000 1.0000 NULL NULL NULL test t1 b vvvvvvvvvvvvv zzzzzzzzzzzzzzzzzz 0.2000 17.1250 6.4000 0 NULL NULL test t1 c aaaa dddddddd 0.1250 6.6571 7.0000 0 NULL NULL test t1 d 1989-03-12 1999-07-23 0.1500 3.0000 8.5000 0 NULL NULL @@ -905,7 +836,7 @@ t1 CREATE TABLE `t1` ( ) ENGINE=MyISAM DEFAULT CHARSET=latin1 COLLATE=latin1_swedish_ci SELECT * FROM mysql.column_stats; db_name table_name column_name min_value max_value nulls_ratio avg_length avg_frequency hist_size hist_type histogram -test t1 a 0 49 0.0000 4.0000 1.0000 0 NULL NULL +test t1 a 0 49 0.0000 4.0000 1.0000 NULL NULL NULL test t1 c aaaa dddddddd 0.1250 6.6571 7.0000 0 NULL NULL test t1 d 1989-03-12 1999-07-23 0.1500 3.0000 8.5000 0 NULL NULL test t1 e 0.01 0.112 0.2250 8.0000 6.2000 0 NULL NULL @@ -916,6 +847,13 @@ test t1 PRIMARY 1 1.0000 test t1 idx2 1 7.0000 test t1 idx2 2 2.3846 test t1 idx3 1 8.5000 +ANALYZE TABLE t1 PERSISTENT FOR COLUMNS(x) INDEXES(); +Table Op Msg_type Msg_text +test.t1 analyze status Engine-independent statistics collected +test.t1 analyze status OK +SELECT * FROM mysql.column_stats where column_name="x"; +db_name table_name column_name min_value max_value nulls_ratio avg_length avg_frequency hist_size hist_type histogram +test t1 x vvvvvvvvvvvvv zzzzzzzzzzzzzzzzzz 0.2000 17.1250 6.4000 0 NULL NULL ALTER TABLE t1 CHANGE COLUMN x b varchar(32); SHOW CREATE TABLE t1; Table Create Table @@ -934,7 +872,7 @@ t1 CREATE TABLE `t1` ( ) ENGINE=MyISAM DEFAULT CHARSET=latin1 COLLATE=latin1_swedish_ci SELECT * FROM mysql.column_stats; db_name table_name column_name min_value max_value nulls_ratio avg_length avg_frequency hist_size hist_type histogram -test t1 a 0 49 0.0000 4.0000 1.0000 0 NULL NULL +test t1 a 0 49 0.0000 4.0000 1.0000 NULL NULL NULL test t1 c aaaa dddddddd 0.1250 6.6571 7.0000 0 NULL NULL test t1 d 1989-03-12 1999-07-23 0.1500 3.0000 8.5000 0 NULL NULL test t1 e 0.01 0.112 0.2250 8.0000 6.2000 0 NULL NULL @@ -951,7 +889,7 @@ test.t1 analyze status Engine-independent statistics collected test.t1 analyze status OK SELECT * FROM mysql.column_stats; db_name table_name column_name min_value max_value nulls_ratio avg_length avg_frequency hist_size hist_type histogram -test t1 a 0 49 0.0000 4.0000 1.0000 0 NULL NULL +test t1 a 0 49 0.0000 4.0000 1.0000 NULL NULL NULL test t1 b vvvvvvvvvvvvv zzzzzzzzzzzzzzzzzz 0.2000 17.1250 6.4000 0 NULL NULL test t1 c aaaa dddddddd 0.1250 6.6571 7.0000 0 NULL NULL test t1 d 1989-03-12 1999-07-23 0.1500 3.0000 8.5000 0 NULL NULL @@ -992,7 +930,7 @@ t1 CREATE TABLE `t1` ( ) ENGINE=MyISAM DEFAULT CHARSET=latin1 COLLATE=latin1_swedish_ci SELECT * FROM mysql.column_stats; db_name table_name column_name min_value max_value nulls_ratio avg_length avg_frequency hist_size hist_type histogram -test t1 a 0 49 0.0000 4.0000 1.0000 0 NULL NULL +test t1 a 0 49 0.0000 4.0000 1.0000 NULL NULL NULL test t1 c aaaa dddddddd 0.1250 6.6571 7.0000 0 NULL NULL test t1 d 1989-03-12 1999-07-23 0.1500 3.0000 8.5000 0 NULL NULL test t1 e 0.01 0.112 0.2250 8.0000 6.2000 0 NULL NULL @@ -1021,7 +959,7 @@ t1 CREATE TABLE `t1` ( ) ENGINE=MyISAM DEFAULT CHARSET=latin1 COLLATE=latin1_swedish_ci SELECT * FROM mysql.column_stats; db_name table_name column_name min_value max_value nulls_ratio avg_length avg_frequency hist_size hist_type histogram -test t1 a 0 49 0.0000 4.0000 1.0000 0 NULL NULL +test t1 a 0 49 0.0000 4.0000 1.0000 NULL NULL NULL test t1 c aaaa dddddddd 0.1250 6.6571 7.0000 0 NULL NULL test t1 d 1989-03-12 1999-07-23 0.1500 3.0000 8.5000 0 NULL NULL test t1 e 0.01 0.112 0.2250 8.0000 6.2000 0 NULL NULL @@ -1032,15 +970,15 @@ test t1 PRIMARY 1 1.0000 test t1 idx2 1 7.0000 test t1 idx2 2 2.3846 test t1 idx3 1 8.5000 -LOAD DATA INFILE 'MYSQLTEST_VARDIR/tmp/save_column_stats' - INTO TABLE mysql.column_stats +LOAD DATA INFILE 'MYSQLTEST_VARDIR/tmp/save_column_stats' IGNORE +INTO TABLE mysql.column_stats FIELDS TERMINATED BY ',' OPTIONALLY ENCLOSED BY '"' LINES TERMINATED BY '\n'; LOAD DATA INFILE 'MYSQLTEST_VARDIR/tmp/save_index_stats' INTO TABLE mysql.index_stats FIELDS TERMINATED BY ',' OPTIONALLY ENCLOSED BY '"' LINES TERMINATED BY '\n'; SELECT * FROM mysql.column_stats; db_name table_name column_name min_value max_value nulls_ratio avg_length avg_frequency hist_size hist_type histogram -test t1 a 0 49 0.0000 4.0000 1.0000 0 NULL NULL +test t1 a 0 49 0.0000 4.0000 1.0000 NULL NULL NULL test t1 b vvvvvvvvvvvvv zzzzzzzzzzzzzzzzzz 0.2000 17.1250 6.4000 0 NULL NULL test t1 c aaaa dddddddd 0.1250 6.6571 7.0000 0 NULL NULL test t1 d 1989-03-12 1999-07-23 0.1500 3.0000 8.5000 0 NULL NULL @@ -1074,7 +1012,7 @@ t1 CREATE TABLE `t1` ( ) ENGINE=MyISAM DEFAULT CHARSET=latin1 COLLATE=latin1_swedish_ci SELECT * FROM mysql.column_stats; db_name table_name column_name min_value max_value nulls_ratio avg_length avg_frequency hist_size hist_type histogram -test t1 a 0 49 0.0000 4.0000 1.0000 0 NULL NULL +test t1 a 0 49 0.0000 4.0000 1.0000 NULL NULL NULL test t1 c aaaa dddddddd 0.1250 6.6571 7.0000 0 NULL NULL test t1 d 1989-03-12 1999-07-23 0.1500 3.0000 8.5000 0 NULL NULL test t1 e 0.01 0.112 0.2250 8.0000 6.2000 0 NULL NULL @@ -1137,7 +1075,7 @@ t1 CREATE TABLE `t1` ( ) ENGINE=MyISAM DEFAULT CHARSET=latin1 COLLATE=latin1_swedish_ci SELECT * FROM mysql.column_stats; db_name table_name column_name min_value max_value nulls_ratio avg_length avg_frequency hist_size hist_type histogram -test t1 a 0 49 0.0000 4.0000 1.0000 0 NULL NULL +test t1 a 0 49 0.0000 4.0000 1.0000 NULL NULL NULL test t1 c aaaa dddddddd 0.1250 6.6571 7.0000 0 NULL NULL test t1 d 1989-03-12 1999-07-23 0.1500 3.0000 8.5000 0 NULL NULL test t1 e 0.01 0.112 0.2250 8.0000 6.2000 0 NULL NULL @@ -1152,7 +1090,7 @@ test.t1 analyze status Engine-independent statistics collected test.t1 analyze status OK SELECT * FROM mysql.column_stats; db_name table_name column_name min_value max_value nulls_ratio avg_length avg_frequency hist_size hist_type histogram -test t1 a 0 49 0.0000 4.0000 1.0000 0 NULL NULL +test t1 a 0 49 0.0000 4.0000 1.0000 NULL NULL NULL test t1 b NULL NULL 1.0000 NULL NULL 0 NULL NULL test t1 c aaaa dddddddd 0.1250 6.6571 7.0000 0 NULL NULL test t1 d 1989-03-12 1999-07-23 0.1500 3.0000 8.5000 0 NULL NULL @@ -1176,7 +1114,7 @@ test.t1 analyze status Engine-independent statistics collected test.t1 analyze status OK SELECT * FROM mysql.column_stats; db_name table_name column_name min_value max_value nulls_ratio avg_length avg_frequency hist_size hist_type histogram -test t1 a 0 49 0.0000 4.0000 1.0000 0 NULL NULL +test t1 a 0 49 0.0000 4.0000 1.0000 NULL NULL NULL test t1 b vvvvvvvvvvvvv zzzzzzzzzzzzzzzzzz 0.2000 17.1250 6.4000 0 NULL NULL test t1 c aaaa dddddddd 0.1250 6.6571 7.0000 0 NULL NULL test t1 d 1989-03-12 1999-07-23 0.1500 3.0000 8.5000 0 NULL NULL @@ -1208,7 +1146,7 @@ t1 CREATE TABLE `t1` ( ) ENGINE=MyISAM DEFAULT CHARSET=latin1 COLLATE=latin1_swedish_ci SELECT * FROM mysql.column_stats; db_name table_name column_name min_value max_value nulls_ratio avg_length avg_frequency hist_size hist_type histogram -test t1 a 0 49 0.0000 4.0000 1.0000 0 NULL NULL +test t1 a 0 49 0.0000 4.0000 1.0000 NULL NULL NULL test t1 c aaaa dddddddd 0.1250 6.6571 7.0000 0 NULL NULL test t1 d 1989-03-12 1999-07-23 0.1500 3.0000 8.5000 0 NULL NULL test t1 e 0.01 0.112 0.2250 8.0000 6.2000 0 NULL NULL @@ -1238,7 +1176,7 @@ t1 CREATE TABLE `t1` ( ) ENGINE=MyISAM DEFAULT CHARSET=latin1 COLLATE=latin1_swedish_ci SELECT * FROM mysql.column_stats; db_name table_name column_name min_value max_value nulls_ratio avg_length avg_frequency hist_size hist_type histogram -test t1 a 0 49 0.0000 4.0000 1.0000 0 NULL NULL +test t1 a 0 49 0.0000 4.0000 1.0000 NULL NULL NULL test t1 c aaaa dddddddd 0.1250 6.6571 7.0000 0 NULL NULL test t1 d 1989-03-12 1999-07-23 0.1500 3.0000 8.5000 0 NULL NULL test t1 e 0.01 0.112 0.2250 8.0000 6.2000 0 NULL NULL @@ -1253,7 +1191,7 @@ test.t1 analyze status Engine-independent statistics collected test.t1 analyze status OK SELECT * FROM mysql.column_stats; db_name table_name column_name min_value max_value nulls_ratio avg_length avg_frequency hist_size hist_type histogram -test t1 a 0 49 0.0000 4.0000 1.0000 0 NULL NULL +test t1 a 0 49 0.0000 4.0000 1.0000 NULL NULL NULL test t1 b vvvvvvvvvvvvv zzzzzzzzzzzzzzzzzz 0.2000 17.1250 6.4000 0 NULL NULL test t1 c aaaa dddddddd 0.1250 6.6571 7.0000 0 NULL NULL test t1 d 1989-03-12 1999-07-23 0.1500 3.0000 8.5000 0 NULL NULL @@ -1335,7 +1273,7 @@ db_name table_name cardinality test t1 40 SELECT * FROM mysql.column_stats; db_name table_name column_name min_value max_value nulls_ratio avg_length avg_frequency hist_size hist_type histogram -test t1 a 0 49 0.0000 4.0000 1.0000 0 NULL NULL +test t1 a 0 49 0.0000 4.0000 1.0000 NULL NULL NULL test t1 b vvvvvvvvvvvvv zzzzzzzzzzzzzzzzzz 0.2000 17.1250 6.4000 0 NULL NULL test t1 c aaaa dddddddd 0.1250 6.6571 7.0000 0 NULL NULL test t1 d 1989-03-12 1999-07-23 0.1500 3.0000 8.5000 0 NULL NULL @@ -1366,8 +1304,8 @@ test t1 40 test t2 40 SELECT * FROM mysql.column_stats ORDER BY column_name, table_name; db_name table_name column_name min_value max_value nulls_ratio avg_length avg_frequency hist_size hist_type histogram -test t1 a 0 49 0.0000 4.0000 1.0000 0 NULL NULL -test t2 a 0 49 0.0000 4.0000 1.0000 0 NULL NULL +test t1 a 0 49 0.0000 4.0000 1.0000 NULL NULL NULL +test t2 a 0 49 0.0000 4.0000 1.0000 NULL NULL NULL test t1 b vvvvvvvvvvvvv zzzzzzzzzzzzzzzzzz 0.2000 17.1250 6.4000 0 NULL NULL test t2 b vvvvvvvvvvvvv zzzzzzzzzzzzzzzzzz 0.2000 17.1250 6.4000 0 NULL NULL test t1 c aaaa dddddddd 0.1250 6.6571 7.0000 0 NULL NULL @@ -1411,7 +1349,7 @@ db_name table_name cardinality test t2 40 SELECT * FROM mysql.column_stats ORDER BY column_name; db_name table_name column_name min_value max_value nulls_ratio avg_length avg_frequency hist_size hist_type histogram -test t2 a 0 49 0.0000 4.0000 1.0000 0 NULL NULL +test t2 a 0 49 0.0000 4.0000 1.0000 NULL NULL NULL test t2 b vvvvvvvvvvvvv zzzzzzzzzzzzzzzzzz 0.2000 17.1250 6.4000 0 NULL NULL test t2 c aaaa dddddddd 0.1250 6.6571 7.0000 0 NULL NULL test t2 d 1989-03-12 1999-07-23 0.1500 3.0000 8.5000 0 NULL NULL @@ -1470,12 +1408,17 @@ test t2 idx4 1 6.2000 test t2 idx4 2 1.7222 test t2 idx4 3 1.1154 test t2 idx4 4 1.0000 +SELECT * FROM mysql.column_stats where column_name="b"; +db_name table_name column_name min_value max_value nulls_ratio avg_length avg_frequency hist_size hist_type histogram +test t2 b vvvvvvvvvvvvv zzzzzzzzzzzzzzzzzz 0.2000 17.1250 6.4000 0 NULL NULL ALTER TABLE t2 CHANGE COLUMN b b varchar(30); SELECT * FROM mysql.index_stats ORDER BY index_name, prefix_arity, table_name; db_name table_name index_name prefix_arity avg_frequency test t2 idx2 1 7.0000 test t2 idx2 2 2.3846 test t2 idx3 1 8.5000 +SELECT * FROM mysql.column_stats where column_name="b"; +db_name table_name column_name min_value max_value nulls_ratio avg_length avg_frequency hist_size hist_type histogram ANALYZE TABLE t2 PERSISTENT FOR COLUMNS ALL INDEXES ALL; Table Op Msg_type Msg_text test.t2 analyze status Engine-independent statistics collected @@ -1511,6 +1454,9 @@ test t2 idx4 1 6.2000 test t2 idx4 2 1.7222 test t2 idx4 3 1.1154 test t2 idx4 4 1.0000 +SELECT * FROM mysql.column_stats where column_name="b"; +db_name table_name column_name min_value max_value nulls_ratio avg_length avg_frequency hist_size hist_type histogram +test t2 b 0 zzzzzzzzzzzzzzzzzz 0.0000 13.9000 6.6667 0 NULL NULL ANALYZE TABLE t2 PERSISTENT FOR COLUMNS ALL INDEXES ALL; Table Op Msg_type Msg_text test.t2 analyze status Engine-independent statistics collected @@ -1584,7 +1530,7 @@ test.t1 analyze Warning Engine-independent statistics are not collected for colu test.t1 analyze status OK SELECT * FROM mysql.column_stats; db_name table_name column_name min_value max_value nulls_ratio avg_length avg_frequency hist_size hist_type histogram -test t1 a 0 49 0.0000 4.0000 1.0000 0 NULL NULL +test t1 a 0 49 0.0000 4.0000 1.0000 NULL NULL NULL test t1 c aaaa dddddddd 0.1250 6.6571 7.0000 0 NULL NULL test t1 d 1989-03-12 1999-07-23 0.1500 3.0000 8.5000 0 NULL NULL test t1 e 0.01 0.112 0.2250 8.0000 6.2000 0 NULL NULL @@ -1640,7 +1586,7 @@ db_name table_name cardinality test t1 40 SELECT * FROM mysql.column_stats; db_name table_name column_name min_value max_value nulls_ratio avg_length avg_frequency hist_size hist_type histogram -test t1 a 0 49 0.0000 4.0000 1.0000 0 NULL NULL +test t1 a 0 49 0.0000 4.0000 1.0000 NULL NULL NULL test t1 c aaaa dddddddd 0.1250 6.6571 7.0000 0 NULL NULL test t1 d 1989-03-12 1999-07-23 0.1500 3.0000 8.5000 0 NULL NULL test t1 e 0.01 0.112 0.2250 8.0000 6.2000 0 NULL NULL @@ -4765,457 +4711,7 @@ set histogram_size=50; ANALYZE TABLE Country, City, CountryLanguage persistent for all; SELECT column_name, min_value, max_value, hist_size, hist_type, histogram FROM mysql.column_stats; column_name min_value max_value hist_size hist_type histogram -Code ABW ZWE 48 JSON_HB { - "target_histogram_size": 50, - "collected_at": "REPLACED", - "collected_by": "REPLACED", - "histogram_hb": [ - { - "start": "ABW", - "size": 0.020920502, - "ndv": 5 - }, - { - "start": "AND", - "size": 0.020920502, - "ndv": 5 - }, - { - "start": "ASM", - "size": 0.020920502, - "ndv": 5 - }, - { - "start": "AUT", - "size": 0.020920502, - "ndv": 5 - }, - { - "start": "BFA", - "size": 0.020920502, - "ndv": 5 - }, - { - "start": "BIH", - "size": 0.020920502, - "ndv": 5 - }, - { - "start": "BRA", - "size": 0.020920502, - "ndv": 5 - }, - { - "start": "BWA", - "size": 0.020920502, - "ndv": 5 - }, - { - "start": "CHL", - "size": 0.020920502, - "ndv": 5 - }, - { - "start": "COG", - "size": 0.020920502, - "ndv": 5 - }, - { - "start": "CRI", - "size": 0.020920502, - "ndv": 5 - }, - { - "start": "CZE", - "size": 0.020920502, - "ndv": 5 - }, - { - "start": "DOM", - "size": 0.020920502, - "ndv": 5 - }, - { - "start": "ESH", - "size": 0.020920502, - "ndv": 5 - }, - { - "start": "FJI", - "size": 0.020920502, - "ndv": 5 - }, - { - "start": "GAB", - "size": 0.020920502, - "ndv": 5 - }, - { - "start": "GIN", - "size": 0.020920502, - "ndv": 5 - }, - { - "start": "GRC", - "size": 0.020920502, - "ndv": 5 - }, - { - "start": "GUM", - "size": 0.020920502, - "ndv": 5 - }, - { - "start": "HRV", - "size": 0.020920502, - "ndv": 5 - }, - { - "start": "IOT", - "size": 0.020920502, - "ndv": 5 - }, - { - "start": "ISR", - "size": 0.020920502, - "ndv": 5 - }, - { - "start": "KAZ", - "size": 0.020920502, - "ndv": 5 - }, - { - "start": "KNA", - "size": 0.020920502, - "ndv": 5 - }, - { - "start": "LBR", - "size": 0.020920502, - "ndv": 5 - }, - { - "start": "LSO", - "size": 0.020920502, - "ndv": 5 - }, - { - "start": "MAR", - "size": 0.020920502, - "ndv": 5 - }, - { - "start": "MEX", - "size": 0.020920502, - "ndv": 5 - }, - { - "start": "MMR", - "size": 0.020920502, - "ndv": 5 - }, - { - "start": "MSR", - "size": 0.020920502, - "ndv": 5 - }, - { - "start": "MYT", - "size": 0.020920502, - "ndv": 5 - }, - { - "start": "NGA", - "size": 0.020920502, - "ndv": 5 - }, - { - "start": "NPL", - "size": 0.020920502, - "ndv": 5 - }, - { - "start": "PAN", - "size": 0.020920502, - "ndv": 5 - }, - { - "start": "PNG", - "size": 0.020920502, - "ndv": 5 - }, - { - "start": "PRY", - "size": 0.020920502, - "ndv": 5 - }, - { - "start": "ROM", - "size": 0.020920502, - "ndv": 5 - }, - { - "start": "SEN", - "size": 0.020920502, - "ndv": 5 - }, - { - "start": "SLB", - "size": 0.020920502, - "ndv": 5 - }, - { - "start": "SPM", - "size": 0.020920502, - "ndv": 5 - }, - { - "start": "SWE", - "size": 0.020920502, - "ndv": 5 - }, - { - "start": "TCD", - "size": 0.020920502, - "ndv": 5 - }, - { - "start": "TKM", - "size": 0.020920502, - "ndv": 5 - }, - { - "start": "TUR", - "size": 0.020920502, - "ndv": 5 - }, - { - "start": "UKR", - "size": 0.020920502, - "ndv": 5 - }, - { - "start": "VAT", - "size": 0.020920502, - "ndv": 5 - }, - { - "start": "VNM", - "size": 0.020920502, - "ndv": 5 - }, - { - "start": "YUG", - "end": "ZWE", - "size": 0.016736402, - "ndv": 4 - } - ] -} -Country ABW ZWE 39 JSON_HB { - "target_histogram_size": 50, - "collected_at": "REPLACED", - "collected_by": "REPLACED", - "histogram_hb": [ - { - "start": "ABW", - "size": 0.020102966, - "ndv": 11 - }, - { - "start": "ATG", - "size": 0.020102966, - "ndv": 14 - }, - { - "start": "BLR", - "size": 0.006619269, - "ndv": 4 - }, - { - "start": "BRA", - "size": 0.061289532, - "ndv": 1 - }, - { - "start": "BRB", - "size": 0.020102966, - "ndv": 9 - }, - { - "start": "CHL", - "size": 0.002206423, - "ndv": 1 - }, - { - "start": "CHN", - "size": 0.0889924, - "ndv": 1 - }, - { - "start": "CIV", - "size": 0.020102966, - "ndv": 10 - }, - { - "start": "CUB", - "size": 0.020102966, - "ndv": 6 - }, - { - "start": "DEU", - "size": 0.020102966, - "ndv": 8 - }, - { - "start": "EGY", - "size": 0.020102966, - "ndv": 4 - }, - { - "start": "ESP", - "size": 0.020102966, - "ndv": 11 - }, - { - "start": "GBR", - "size": 0.020102966, - "ndv": 3 - }, - { - "start": "GIB", - "size": 0.020102966, - "ndv": 19 - }, - { - "start": "IDN", - "size": 0.012503064, - "ndv": 1 - }, - { - "start": "IND", - "size": 0.083598921, - "ndv": 1 - }, - { - "start": "IRL", - "size": 0.020102966, - "ndv": 3 - }, - { - "start": "IRQ", - "size": 0.020102966, - "ndv": 6 - }, - { - "start": "JOR", - "size": 2.451581e-4, - "ndv": 1 - }, - { - "start": "JPN", - "size": 0.060799215, - "ndv": 1 - }, - { - "start": "KAZ", - "size": 0.020102966, - "ndv": 7 - }, - { - "start": "KOR", - "size": 0.020102966, - "ndv": 16 - }, - { - "start": "MDA", - "size": 0.002451581, - "ndv": 3 - }, - { - "start": "MEX", - "size": 0.042412356, - "ndv": 1 - }, - { - "start": "MHL", - "size": 0.020102966, - "ndv": 20 - }, - { - "start": "NGA", - "size": 0.020102966, - "ndv": 4 - }, - { - "start": "NLD", - "size": 0.020102966, - "ndv": 7 - }, - { - "start": "PAK", - "size": 0.007354744, - "ndv": 4 - }, - { - "start": "PHL", - "size": 0.033341505, - "ndv": 1 - }, - { - "start": "PLW", - "size": 0.020102966, - "ndv": 8 - }, - { - "start": "PSE", - "size": 0.008580534, - "ndv": 5 - }, - { - "start": "RUS", - "size": 0.046334886, - "ndv": 1 - }, - { - "start": "RWA", - "size": 0.020102966, - "ndv": 18 - }, - { - "start": "SWE", - "size": 0.020102966, - "ndv": 16 - }, - { - "start": "TUR", - "size": 0.020102966, - "ndv": 4 - }, - { - "start": "TZA", - "size": 0.015199804, - "ndv": 4 - }, - { - "start": "USA", - "size": 0.067173327, - "ndv": 1 - }, - { - "start": "UZB", - "size": 0.020102966, - "ndv": 7 - }, - { - "start": "VNM", - "end": "ZWE", - "size": 0.018632018, - "ndv": 9 - } - ] -} +Code ABW ZWE NULL NULL NULL Name Afghanistan Zimbabwe 48 JSON_HB { "target_histogram_size": 50, "collected_at": "REPLACED", @@ -5464,6 +4960,210 @@ Name Afghanistan Zimbabwe 48 JSON_HB { } ] } +ID 1 4079 NULL NULL NULL +Country ABW ZWE 39 JSON_HB { + "target_histogram_size": 50, + "collected_at": "REPLACED", + "collected_by": "REPLACED", + "histogram_hb": [ + { + "start": "ABW", + "size": 0.020102966, + "ndv": 11 + }, + { + "start": "ATG", + "size": 0.020102966, + "ndv": 14 + }, + { + "start": "BLR", + "size": 0.006619269, + "ndv": 4 + }, + { + "start": "BRA", + "size": 0.061289532, + "ndv": 1 + }, + { + "start": "BRB", + "size": 0.020102966, + "ndv": 9 + }, + { + "start": "CHL", + "size": 0.002206423, + "ndv": 1 + }, + { + "start": "CHN", + "size": 0.0889924, + "ndv": 1 + }, + { + "start": "CIV", + "size": 0.020102966, + "ndv": 10 + }, + { + "start": "CUB", + "size": 0.020102966, + "ndv": 6 + }, + { + "start": "DEU", + "size": 0.020102966, + "ndv": 8 + }, + { + "start": "EGY", + "size": 0.020102966, + "ndv": 4 + }, + { + "start": "ESP", + "size": 0.020102966, + "ndv": 11 + }, + { + "start": "GBR", + "size": 0.020102966, + "ndv": 3 + }, + { + "start": "GIB", + "size": 0.020102966, + "ndv": 19 + }, + { + "start": "IDN", + "size": 0.012503064, + "ndv": 1 + }, + { + "start": "IND", + "size": 0.083598921, + "ndv": 1 + }, + { + "start": "IRL", + "size": 0.020102966, + "ndv": 3 + }, + { + "start": "IRQ", + "size": 0.020102966, + "ndv": 6 + }, + { + "start": "JOR", + "size": 2.451581e-4, + "ndv": 1 + }, + { + "start": "JPN", + "size": 0.060799215, + "ndv": 1 + }, + { + "start": "KAZ", + "size": 0.020102966, + "ndv": 7 + }, + { + "start": "KOR", + "size": 0.020102966, + "ndv": 16 + }, + { + "start": "MDA", + "size": 0.002451581, + "ndv": 3 + }, + { + "start": "MEX", + "size": 0.042412356, + "ndv": 1 + }, + { + "start": "MHL", + "size": 0.020102966, + "ndv": 20 + }, + { + "start": "NGA", + "size": 0.020102966, + "ndv": 4 + }, + { + "start": "NLD", + "size": 0.020102966, + "ndv": 7 + }, + { + "start": "PAK", + "size": 0.007354744, + "ndv": 4 + }, + { + "start": "PHL", + "size": 0.033341505, + "ndv": 1 + }, + { + "start": "PLW", + "size": 0.020102966, + "ndv": 8 + }, + { + "start": "PSE", + "size": 0.008580534, + "ndv": 5 + }, + { + "start": "RUS", + "size": 0.046334886, + "ndv": 1 + }, + { + "start": "RWA", + "size": 0.020102966, + "ndv": 18 + }, + { + "start": "SWE", + "size": 0.020102966, + "ndv": 16 + }, + { + "start": "TUR", + "size": 0.020102966, + "ndv": 4 + }, + { + "start": "TZA", + "size": 0.015199804, + "ndv": 4 + }, + { + "start": "USA", + "size": 0.067173327, + "ndv": 1 + }, + { + "start": "UZB", + "size": 0.020102966, + "ndv": 7 + }, + { + "start": "VNM", + "end": "ZWE", + "size": 0.018632018, + "ndv": 9 + } + ] +} SurfaceArea 0.40 17075400.00 48 JSON_HB { "target_histogram_size": 50, "collected_at": "REPLACED", @@ -6203,264 +5903,6 @@ Capital 1 4074 47 JSON_HB { } ] } -ID 1 4079 50 JSON_HB { - "target_histogram_size": 50, - "collected_at": "REPLACED", - "collected_by": "REPLACED", - "histogram_hb": [ - { - "start": "1", - "size": 0.020102966, - "ndv": 82 - }, - { - "start": "83", - "size": 0.020102966, - "ndv": 82 - }, - { - "start": "165", - "size": 0.020102966, - "ndv": 82 - }, - { - "start": "247", - "size": 0.020102966, - "ndv": 82 - }, - { - "start": "329", - "size": 0.020102966, - "ndv": 82 - }, - { - "start": "411", - "size": 0.020102966, - "ndv": 82 - }, - { - "start": "493", - "size": 0.020102966, - "ndv": 82 - }, - { - "start": "575", - "size": 0.020102966, - "ndv": 82 - }, - { - "start": "657", - "size": 0.020102966, - "ndv": 82 - }, - { - "start": "739", - "size": 0.020102966, - "ndv": 82 - }, - { - "start": "821", - "size": 0.020102966, - "ndv": 82 - }, - { - "start": "903", - "size": 0.020102966, - "ndv": 82 - }, - { - "start": "985", - "size": 0.020102966, - "ndv": 82 - }, - { - "start": "1067", - "size": 0.020102966, - "ndv": 82 - }, - { - "start": "1149", - "size": 0.020102966, - "ndv": 82 - }, - { - "start": "1231", - "size": 0.020102966, - "ndv": 82 - }, - { - "start": "1313", - "size": 0.020102966, - "ndv": 82 - }, - { - "start": "1395", - "size": 0.020102966, - "ndv": 82 - }, - { - "start": "1477", - "size": 0.020102966, - "ndv": 82 - }, - { - "start": "1559", - "size": 0.020102966, - "ndv": 82 - }, - { - "start": "1641", - "size": 0.020102966, - "ndv": 82 - }, - { - "start": "1723", - "size": 0.020102966, - "ndv": 82 - }, - { - "start": "1805", - "size": 0.020102966, - "ndv": 82 - }, - { - "start": "1887", - "size": 0.020102966, - "ndv": 82 - }, - { - "start": "1969", - "size": 0.020102966, - "ndv": 82 - }, - { - "start": "2051", - "size": 0.020102966, - "ndv": 82 - }, - { - "start": "2133", - "size": 0.020102966, - "ndv": 82 - }, - { - "start": "2215", - "size": 0.020102966, - "ndv": 82 - }, - { - "start": "2297", - "size": 0.020102966, - "ndv": 82 - }, - { - "start": "2379", - "size": 0.020102966, - "ndv": 82 - }, - { - "start": "2461", - "size": 0.020102966, - "ndv": 82 - }, - { - "start": "2543", - "size": 0.020102966, - "ndv": 82 - }, - { - "start": "2625", - "size": 0.020102966, - "ndv": 82 - }, - { - "start": "2707", - "size": 0.020102966, - "ndv": 82 - }, - { - "start": "2789", - "size": 0.020102966, - "ndv": 82 - }, - { - "start": "2871", - "size": 0.020102966, - "ndv": 82 - }, - { - "start": "2953", - "size": 0.020102966, - "ndv": 82 - }, - { - "start": "3035", - "size": 0.020102966, - "ndv": 82 - }, - { - "start": "3117", - "size": 0.020102966, - "ndv": 82 - }, - { - "start": "3199", - "size": 0.020102966, - "ndv": 82 - }, - { - "start": "3281", - "size": 0.020102966, - "ndv": 82 - }, - { - "start": "3363", - "size": 0.020102966, - "ndv": 82 - }, - { - "start": "3445", - "size": 0.020102966, - "ndv": 82 - }, - { - "start": "3527", - "size": 0.020102966, - "ndv": 82 - }, - { - "start": "3609", - "size": 0.020102966, - "ndv": 82 - }, - { - "start": "3691", - "size": 0.020102966, - "ndv": 82 - }, - { - "start": "3773", - "size": 0.020102966, - "ndv": 82 - }, - { - "start": "3855", - "size": 0.020102966, - "ndv": 82 - }, - { - "start": "3937", - "size": 0.020102966, - "ndv": 82 - }, - { - "start": "4019", - "end": "4079", - "size": 0.014954646, - "ndv": 61 - } - ] -} Name A Coruña (La Coruña) Ürgenc 50 JSON_HB { "target_histogram_size": 50, "collected_at": "REPLACED", @@ -7728,10 +7170,10 @@ Percentage 0.0 99.9 47 JSON_HB { } analyze select * from Country use index () where Code between 'BBC' and 'GGG'; id select_type table type possible_keys key key_len ref rows r_rows filtered r_filtered Extra -1 SIMPLE Country ALL NULL NULL NULL NULL 239 239.00 24.58 25.52 Using where +1 SIMPLE Country ALL NULL NULL NULL NULL 239 239.00 20.00 25.52 Using where analyze select * from Country use index () where Code < 'BBC'; id select_type table type possible_keys key key_len ref rows r_rows filtered r_filtered Extra -1 SIMPLE Country ALL NULL NULL NULL NULL 239 239.00 8.37 7.11 Using where +1 SIMPLE Country ALL NULL NULL NULL NULL 239 239.00 4.00 7.11 Using where set histogram_type=@save_histogram_type; set histogram_size=@save_histogram_size; DROP SCHEMA world; @@ -8294,6 +7736,8 @@ analyze table t1 persistent for all; Table Op Msg_type Msg_text test.t1 analyze status Engine-independent statistics collected test.t1 analyze status OK +Warnings: +Warning 1292 Truncated incorrect INTEGER value: '13715197108439488792' select histogram from mysql.column_stats where table_name='t1' and db_name=database(); histogram diff --git a/mysql-test/main/status2.result b/mysql-test/main/status2.result index 60309e14fe3..78d658a7605 100644 --- a/mysql-test/main/status2.result +++ b/mysql-test/main/status2.result @@ -83,3 +83,121 @@ variable_value < 1024*1024*1024 # # End of 10.2 tests # +# +# MDEV-32441 SENT_ROWS shows random wrong values when stored function +# is selected +# +create table t1 (a int) engine=aria; +insert into t1 values (1),(2),(3),(4),(5),(6),(7); +flush status; +create function if not exists f() returns int return +( +select sum(a) > 0 from t1 +); +select f() from seq_1_to_10 where seq%5 = 0; +f() +1 +1 +show status like "rows_sent"; +Variable_name Value +Rows_sent 2 +# Test simple query +set debug_sync='RESET'; +connect con1,localhost,root,,; +set debug_sync='end_of_statement SIGNAL parked WAIT_FOR go'; +select f() from seq_1_to_10 where seq%5 = 0; +connection default; +set debug_sync='now WAIT_FOR parked'; +# Result should be 2, 10+7*2=24 +select sent_rows, examined_rows from information_schema.processlist where id=#; +sent_rows examined_rows +2 24 +set debug_sync='now signal go'; +connection con1; +f() +1 +1 +# Test union +set debug_sync='end_of_statement SIGNAL parked WAIT_FOR go'; +select a from t1 where a not in (1,2,3,4) union select a from t1 where a not in (4,5,6,7); +connection default; +set debug_sync='now WAIT_FOR parked'; +# Result should be 6, 7+7+6=20 (2 scans of 7 rows + 6 rows in union) +select sent_rows, examined_rows from information_schema.processlist where id=#; +sent_rows examined_rows +6 20 +set debug_sync='now signal go'; +connection con1; +a +5 +6 +7 +1 +2 +3 +# Test handler calls +handler t1 open; +set debug_sync='end_of_statement SIGNAL parked WAIT_FOR go'; +handler t1 read NEXT LIMIT 2,4; +connection default; +set debug_sync='now WAIT_FOR parked'; +# Result should be 2, 10+7*2=24 +select sent_rows, examined_rows from information_schema.processlist where id=#; +sent_rows examined_rows +4 6 +set debug_sync='now signal go'; +connection con1; +a +3 +4 +5 +6 +handler t1 close; +connection default; +drop function f; +drop table t1; +# Test Stored procedures +create or replace table t (a int primary key); +insert into t select seq from seq_1_to_100; +create procedure pr() +begin +select * from t where a between 1 and 2 ; +select * from t where a between 4 and 6 ; +end $ +connection con1; +flush status; +set debug_sync='end_of_statement SIGNAL parked WAIT_FOR go EXECUTE 2'; +call pr(); +connection default; +set debug_sync='now WAIT_FOR parked'; +select examined_rows, sent_rows, info from information_schema.processlist where id=#; +examined_rows sent_rows info +2 2 select * from t where a between 1 and 2 +set debug_sync='now signal go'; +select examined_rows, sent_rows, info from information_schema.processlist where id=#; +examined_rows sent_rows info +3 3 select * from t where a between 4 and 6 +set debug_sync='now signal go'; +connection con1; +a +1 +2 +a +4 +5 +6 +show status like '%rows%'; +Variable_name Value +Not_flushed_delayed_rows 0 +Rows_read 8 +Rows_sent 5 +Rows_tmp_read 0 +Sort_rows 0 +connection default; +drop table t; +drop procedure pr; +disconnect con1; +set debug_sync= RESET; +# +# End of 11.3 tests +# diff --git a/mysql-test/main/status2.test b/mysql-test/main/status2.test index 339e853f2fc..1cc53b2bc13 100644 --- a/mysql-test/main/status2.test +++ b/mysql-test/main/status2.test @@ -1,4 +1,7 @@ --source include/not_embedded.inc +--source include/have_sequence.inc +--source include/have_debug_sync.inc +--source include/have_sequence.inc --echo # --echo # Bug#24289 Status Variable "Questions" gets wrong values with Stored Routines @@ -77,3 +80,112 @@ select variable_value < 1024*1024*1024 from information_schema.global_status whe --echo # End of 10.2 tests --echo # +--echo # +--echo # MDEV-32441 SENT_ROWS shows random wrong values when stored function +--echo # is selected +--echo # + +create table t1 (a int) engine=aria; +insert into t1 values (1),(2),(3),(4),(5),(6),(7); +flush status; +create function if not exists f() returns int return +( + select sum(a) > 0 from t1 +); + +--disable_ps_protocol +select f() from seq_1_to_10 where seq%5 = 0; +show status like "rows_sent"; +--enable_ps_protocol + +--echo # Test simple query + +set debug_sync='RESET'; +--connect(con1,localhost,root,,) +--let $conid= `select connection_id()` +--let $replace_conid=id=$conid +set debug_sync='end_of_statement SIGNAL parked WAIT_FOR go'; +--send select f() from seq_1_to_10 where seq%5 = 0 + +--connection default +set debug_sync='now WAIT_FOR parked'; +--echo # Result should be 2, 10+7*2=24 +--replace_result $replace_conid id=# +eval select sent_rows, examined_rows from information_schema.processlist where id=$conid; +set debug_sync='now signal go'; +--connection con1 +--reap + +--echo # Test union + +set debug_sync='end_of_statement SIGNAL parked WAIT_FOR go'; +--send select a from t1 where a not in (1,2,3,4) union select a from t1 where a not in (4,5,6,7) +--connection default +set debug_sync='now WAIT_FOR parked'; +--echo # Result should be 6, 7+7+6=20 (2 scans of 7 rows + 6 rows in union) +--replace_result $replace_conid id=# +eval select sent_rows, examined_rows from information_schema.processlist where id=$conid; +set debug_sync='now signal go'; +--connection con1 +--reap + +--echo # Test handler calls +handler t1 open; +set debug_sync='end_of_statement SIGNAL parked WAIT_FOR go'; +--send handler t1 read NEXT LIMIT 2,4 +--connection default +set debug_sync='now WAIT_FOR parked'; +--echo # Result should be 2, 10+7*2=24 +--replace_result $replace_conid id=# +eval select sent_rows, examined_rows from information_schema.processlist where id=$conid; +set debug_sync='now signal go'; +--connection con1 +--reap +handler t1 close; + +--connection default +drop function f; +drop table t1; + +--echo # Test Stored procedures + +create or replace table t (a int primary key); +insert into t select seq from seq_1_to_100; +--delimiter $ +create procedure pr() +begin + select * from t where a between 1 and 2 ; + select * from t where a between 4 and 6 ; +end $ +--delimiter ; + +--connection con1 +flush status; +set debug_sync='end_of_statement SIGNAL parked WAIT_FOR go EXECUTE 2'; + +--send call pr() + +--connection default +set debug_sync='now WAIT_FOR parked'; +--replace_result $replace_conid id=# +eval select examined_rows, sent_rows, info from information_schema.processlist where id=$conid; +set debug_sync='now signal go'; +--replace_result $replace_conid id=# +eval select examined_rows, sent_rows, info from information_schema.processlist where id=$conid; +set debug_sync='now signal go'; + +--connection con1 +--reap +show status like '%rows%'; + +connection default; +# Cleanup +drop table t; +drop procedure pr; + +--disconnect con1 +set debug_sync= RESET; + +--echo # +--echo # End of 11.3 tests +--echo # diff --git a/mysql-test/main/subselect3.inc b/mysql-test/main/subselect3.inc index 98ebbe2442e..8bb84eb24d9 100644 --- a/mysql-test/main/subselect3.inc +++ b/mysql-test/main/subselect3.inc @@ -646,14 +646,14 @@ DROP TABLE t1, t2; create table t1 (a int, b decimal(13, 3)); insert into t1 values (1, 0.123); --disable_ps2_protocol -select a, (select max(b) from t1) into outfile "subselect.out.file.1" from t1; +select a, (select max(b) from t1) into outfile "../../tmp/subselect.out.file.1" from t1; --enable_ps2_protocol delete from t1; -load data infile "subselect.out.file.1" into table t1; +load data infile "../../tmp/subselect.out.file.1" into table t1; select * from t1; drop table t1; let $datadir=`select @@datadir`; ---remove_file $datadir/test/subselect.out.file.1 +--remove_file $MYSQLTEST_VARDIR/tmp/subselect.out.file.1 # # Bug #37894: Assertion in init_read_record_seq in handler.h line 1444 diff --git a/mysql-test/main/subselect3.result b/mysql-test/main/subselect3.result index 8e640e7803f..4c654cb736f 100644 --- a/mysql-test/main/subselect3.result +++ b/mysql-test/main/subselect3.result @@ -805,9 +805,9 @@ SELECT 1 FROM t1 WHERE t1.a NOT IN (SELECT 1 FROM t1, t2 WHERE 0); DROP TABLE t1, t2; create table t1 (a int, b decimal(13, 3)); insert into t1 values (1, 0.123); -select a, (select max(b) from t1) into outfile "subselect.out.file.1" from t1; +select a, (select max(b) from t1) into outfile "../../tmp/subselect.out.file.1" from t1; delete from t1; -load data infile "subselect.out.file.1" into table t1; +load data infile "../../tmp/subselect.out.file.1" into table t1; select * from t1; a b 1 0.123 diff --git a/mysql-test/main/subselect3_jcl6.result b/mysql-test/main/subselect3_jcl6.result index 470e51ef9c3..b606f0a5127 100644 --- a/mysql-test/main/subselect3_jcl6.result +++ b/mysql-test/main/subselect3_jcl6.result @@ -808,9 +808,9 @@ SELECT 1 FROM t1 WHERE t1.a NOT IN (SELECT 1 FROM t1, t2 WHERE 0); DROP TABLE t1, t2; create table t1 (a int, b decimal(13, 3)); insert into t1 values (1, 0.123); -select a, (select max(b) from t1) into outfile "subselect.out.file.1" from t1; +select a, (select max(b) from t1) into outfile "../../tmp/subselect.out.file.1" from t1; delete from t1; -load data infile "subselect.out.file.1" into table t1; +load data infile "../../tmp/subselect.out.file.1" into table t1; select * from t1; a b 1 0.123 diff --git a/mysql-test/main/subselect_sj2.result b/mysql-test/main/subselect_sj2.result index 978f4b72a98..1ee106aa6e8 100644 --- a/mysql-test/main/subselect_sj2.result +++ b/mysql-test/main/subselect_sj2.result @@ -969,6 +969,8 @@ id select_type table type possible_keys key key_len ref rows Extra 1 PRIMARY t2 index PRIMARY,d d 9 NULL 17 Using where; Using index; LooseScan 1 PRIMARY t1 ref a a 5 test.t2.d 1 Using where; Using index; FirstMatch(t2) 1 PRIMARY t1 ref b b 4 test.t2.d 1 +Warnings: +Note 1105 Cannot use key `d` part[0] for lookup: `test`.`t2`.`d` of type `varchar` = "`t1`.`a`" of type `int` explain SELECT * FROM t1 WHERE b IN ( SELECT d FROM t2, t1 @@ -978,6 +980,8 @@ id select_type table type possible_keys key key_len ref rows Extra 1 PRIMARY t2 index_merge PRIMARY,d d,PRIMARY 4,4 NULL 2 Using sort_union(d,PRIMARY); Using where; Start temporary 1 PRIMARY t1 ref a a 5 test.t2.d 1 Using where; Using index 1 PRIMARY t1 ref b b 4 test.t2.d 1 End temporary +Warnings: +Note 1105 Cannot use key `d` part[0] for lookup: `test`.`t2`.`d` of type `varchar` = "`t1`.`a`" of type `int` SELECT * FROM t1 WHERE b IN ( SELECT d FROM t2, t1 WHERE a = d AND ( pk < 2 OR d = 'z' ) and f > 0 diff --git a/mysql-test/main/subselect_sj2_jcl6.result b/mysql-test/main/subselect_sj2_jcl6.result index c4d121616e7..34cfe2d1145 100644 --- a/mysql-test/main/subselect_sj2_jcl6.result +++ b/mysql-test/main/subselect_sj2_jcl6.result @@ -976,6 +976,8 @@ id select_type table type possible_keys key key_len ref rows Extra 1 PRIMARY t2 index PRIMARY,d d 9 NULL 17 Using where; Using index; LooseScan 1 PRIMARY t1 ref a a 5 test.t2.d 1 Using where; Using index; FirstMatch(t2) 1 PRIMARY t1 ref b b 4 test.t2.d 1 Using join buffer (flat, BKA join); Key-ordered Rowid-ordered scan +Warnings: +Note 1105 Cannot use key `d` part[0] for lookup: `test`.`t2`.`d` of type `varchar` = "`t1`.`a`" of type `int` explain SELECT * FROM t1 WHERE b IN ( SELECT d FROM t2, t1 @@ -985,6 +987,8 @@ id select_type table type possible_keys key key_len ref rows Extra 1 PRIMARY t2 index_merge PRIMARY,d d,PRIMARY 4,4 NULL 2 Using sort_union(d,PRIMARY); Using where; Start temporary 1 PRIMARY t1 ref a a 5 test.t2.d 1 Using where; Using index 1 PRIMARY t1 ref b b 4 test.t2.d 1 End temporary; Using join buffer (flat, BKA join); Key-ordered Rowid-ordered scan +Warnings: +Note 1105 Cannot use key `d` part[0] for lookup: `test`.`t2`.`d` of type `varchar` = "`t1`.`a`" of type `int` SELECT * FROM t1 WHERE b IN ( SELECT d FROM t2, t1 WHERE a = d AND ( pk < 2 OR d = 'z' ) and f > 0 diff --git a/mysql-test/main/subselect_sj2_mat.result b/mysql-test/main/subselect_sj2_mat.result index c639b384522..d022820e1fd 100644 --- a/mysql-test/main/subselect_sj2_mat.result +++ b/mysql-test/main/subselect_sj2_mat.result @@ -971,6 +971,8 @@ id select_type table type possible_keys key key_len ref rows Extra 1 PRIMARY t2 index PRIMARY,d d 9 NULL 17 Using where; Using index; LooseScan 1 PRIMARY t1 ref a a 5 test.t2.d 1 Using where; Using index; FirstMatch(t2) 1 PRIMARY t1 ref b b 4 test.t2.d 1 +Warnings: +Note 1105 Cannot use key `d` part[0] for lookup: `test`.`t2`.`d` of type `varchar` = "`t1`.`a`" of type `int` explain SELECT * FROM t1 WHERE b IN ( SELECT d FROM t2, t1 @@ -980,6 +982,8 @@ id select_type table type possible_keys key key_len ref rows Extra 1 PRIMARY t2 index_merge PRIMARY,d d,PRIMARY 4,4 NULL 2 Using sort_union(d,PRIMARY); Using where; Start temporary 1 PRIMARY t1 ref a a 5 test.t2.d 1 Using where; Using index 1 PRIMARY t1 ref b b 4 test.t2.d 1 End temporary +Warnings: +Note 1105 Cannot use key `d` part[0] for lookup: `test`.`t2`.`d` of type `varchar` = "`t1`.`a`" of type `int` SELECT * FROM t1 WHERE b IN ( SELECT d FROM t2, t1 WHERE a = d AND ( pk < 2 OR d = 'z' ) and f > 0 diff --git a/mysql-test/main/system_mysql_db.result b/mysql-test/main/system_mysql_db.result index b89381da5c3..fb54069ba97 100644 --- a/mysql-test/main/system_mysql_db.result +++ b/mysql-test/main/system_mysql_db.result @@ -57,6 +57,7 @@ db CREATE TABLE `db` ( `Event_priv` enum('N','Y') CHARACTER SET utf8mb3 COLLATE utf8mb3_general_ci NOT NULL DEFAULT 'N', `Trigger_priv` enum('N','Y') CHARACTER SET utf8mb3 COLLATE utf8mb3_general_ci NOT NULL DEFAULT 'N', `Delete_history_priv` enum('N','Y') CHARACTER SET utf8mb3 COLLATE utf8mb3_general_ci NOT NULL DEFAULT 'N', + `Show_create_routine_priv` enum('N','Y') CHARACTER SET utf8mb3 COLLATE utf8mb3_general_ci NOT NULL DEFAULT 'N', PRIMARY KEY (`Host`,`Db`,`User`), KEY `User` (`User`) ) ENGINE=Aria DEFAULT CHARSET=utf8mb3 COLLATE=utf8mb3_bin PAGE_CHECKSUM=1 TRANSACTIONAL=1 COMMENT='Database privileges' @@ -115,7 +116,7 @@ procs_priv CREATE TABLE `procs_priv` ( `Routine_name` char(64) CHARACTER SET utf8mb3 COLLATE utf8mb3_general_ci NOT NULL DEFAULT '', `Routine_type` enum('FUNCTION','PROCEDURE','PACKAGE','PACKAGE BODY') NOT NULL, `Grantor` varchar(384) NOT NULL DEFAULT '', - `Proc_priv` set('Execute','Alter Routine','Grant') CHARACTER SET utf8mb3 COLLATE utf8mb3_general_ci NOT NULL DEFAULT '', + `Proc_priv` set('Execute','Alter Routine','Grant','Show Create Routine') CHARACTER SET utf8mb3 COLLATE utf8mb3_general_ci NOT NULL DEFAULT '', `Timestamp` timestamp NOT NULL DEFAULT current_timestamp() ON UPDATE current_timestamp(), PRIMARY KEY (`Host`,`Db`,`User`,`Routine_name`,`Routine_type`), KEY `Grantor` (`Grantor`) @@ -204,15 +205,15 @@ slow_log CREATE TABLE `slow_log` ( `user_host` mediumtext NOT NULL, `query_time` time(6) NOT NULL, `lock_time` time(6) NOT NULL, - `rows_sent` int(11) NOT NULL, - `rows_examined` int(11) NOT NULL, + `rows_sent` bigint(20) unsigned NOT NULL, + `rows_examined` bigint(20) unsigned NOT NULL, `db` varchar(512) NOT NULL, `last_insert_id` int(11) NOT NULL, `insert_id` int(11) NOT NULL, `server_id` int(10) unsigned NOT NULL, `sql_text` mediumtext NOT NULL, `thread_id` bigint(21) unsigned NOT NULL, - `rows_affected` int(11) NOT NULL + `rows_affected` bigint(20) unsigned NOT NULL ) ENGINE=CSV DEFAULT CHARSET=utf8mb3 COLLATE=utf8mb3_general_ci COMMENT='Slow log' show create table table_stats; Table Create Table diff --git a/mysql-test/main/system_mysql_db_error_log.result b/mysql-test/main/system_mysql_db_error_log.result index c2129b7df31..8a15dad9ce0 100644 --- a/mysql-test/main/system_mysql_db_error_log.result +++ b/mysql-test/main/system_mysql_db_error_log.result @@ -15,7 +15,7 @@ SET @all_known_privileges_current=(SELECT CAST(json_value(Priv, '$.access') AS U DROP USER user1@localhost; SELECT HEX(@all_known_privileges_current); HEX(@all_known_privileges_current) -7FFFFFFFFF +FFFFFFFFFF CREATE USER bad_access1@localhost; UPDATE mysql.global_priv @@ -90,11 +90,11 @@ host='localhost' and user='good_version_id_100400'; FLUSH PRIVILEGES; SHOW GRANTS FOR good_version_id_100400@localhost; Grants for good_version_id_100400@localhost -GRANT ALL PRIVILEGES ON *.* TO `good_version_id_100400`@`localhost` WITH GRANT OPTION +GRANT SELECT, INSERT, UPDATE, DELETE, CREATE, DROP, RELOAD, SHUTDOWN, PROCESS, FILE, REFERENCES, INDEX, ALTER, SHOW DATABASES, SUPER, CREATE TEMPORARY TABLES, LOCK TABLES, EXECUTE, REPLICATION SLAVE, BINLOG MONITOR, CREATE VIEW, SHOW VIEW, CREATE ROUTINE, ALTER ROUTINE, CREATE USER, EVENT, TRIGGER, CREATE TABLESPACE, DELETE HISTORY, SET USER, FEDERATED ADMIN, CONNECTION ADMIN, READ_ONLY ADMIN, REPLICATION SLAVE ADMIN, REPLICATION MASTER ADMIN, BINLOG ADMIN, BINLOG REPLAY, SLAVE MONITOR ON *.* TO `good_version_id_100400`@`localhost` WITH GRANT OPTION GRANT REPLICATION MASTER ADMIN ON *.* TO good_version_id_100400@localhost; SHOW GRANTS FOR good_version_id_100400@localhost; Grants for good_version_id_100400@localhost -GRANT ALL PRIVILEGES ON *.* TO `good_version_id_100400`@`localhost` WITH GRANT OPTION +GRANT SELECT, INSERT, UPDATE, DELETE, CREATE, DROP, RELOAD, SHUTDOWN, PROCESS, FILE, REFERENCES, INDEX, ALTER, SHOW DATABASES, SUPER, CREATE TEMPORARY TABLES, LOCK TABLES, EXECUTE, REPLICATION SLAVE, BINLOG MONITOR, CREATE VIEW, SHOW VIEW, CREATE ROUTINE, ALTER ROUTINE, CREATE USER, EVENT, TRIGGER, CREATE TABLESPACE, DELETE HISTORY, SET USER, FEDERATED ADMIN, CONNECTION ADMIN, READ_ONLY ADMIN, REPLICATION SLAVE ADMIN, REPLICATION MASTER ADMIN, BINLOG ADMIN, BINLOG REPLAY, SLAVE MONITOR ON *.* TO `good_version_id_100400`@`localhost` WITH GRANT OPTION DROP USER good_version_id_100400@localhost; CREATE USER good_version_id_100500@localhost; GRANT SUPER ON *.* to good_version_id_100500@localhost; diff --git a/mysql-test/main/system_mysql_db_fix40123.result b/mysql-test/main/system_mysql_db_fix40123.result index 2ed1e8ae618..9688038c492 100644 --- a/mysql-test/main/system_mysql_db_fix40123.result +++ b/mysql-test/main/system_mysql_db_fix40123.result @@ -95,6 +95,7 @@ db CREATE TABLE `db` ( `Event_priv` enum('N','Y') CHARACTER SET utf8mb3 COLLATE utf8mb3_general_ci NOT NULL DEFAULT 'N', `Trigger_priv` enum('N','Y') CHARACTER SET utf8mb3 COLLATE utf8mb3_general_ci NOT NULL DEFAULT 'N', `Delete_history_priv` enum('N','Y') CHARACTER SET utf8mb3 COLLATE utf8mb3_general_ci NOT NULL DEFAULT 'N', + `Show_create_routine_priv` enum('N','Y') CHARACTER SET utf8mb3 COLLATE utf8mb3_general_ci NOT NULL DEFAULT 'N', PRIMARY KEY (`Host`,`Db`,`User`), KEY `User` (`User`) ) ENGINE=Aria DEFAULT CHARSET=utf8mb3 COLLATE=utf8mb3_bin PAGE_CHECKSUM=1 TRANSACTIONAL=1 COMMENT='Database privileges' @@ -153,7 +154,7 @@ procs_priv CREATE TABLE `procs_priv` ( `Routine_name` char(64) CHARACTER SET utf8mb3 COLLATE utf8mb3_general_ci NOT NULL DEFAULT '', `Routine_type` enum('FUNCTION','PROCEDURE','PACKAGE','PACKAGE BODY') NOT NULL, `Grantor` varchar(384) NOT NULL DEFAULT '', - `Proc_priv` set('Execute','Alter Routine','Grant') CHARACTER SET utf8mb3 COLLATE utf8mb3_general_ci NOT NULL DEFAULT '', + `Proc_priv` set('Execute','Alter Routine','Grant','Show Create Routine') CHARACTER SET utf8mb3 COLLATE utf8mb3_general_ci NOT NULL DEFAULT '', `Timestamp` timestamp NOT NULL DEFAULT current_timestamp() ON UPDATE current_timestamp(), PRIMARY KEY (`Host`,`Db`,`User`,`Routine_name`,`Routine_type`), KEY `Grantor` (`Grantor`) @@ -242,15 +243,15 @@ slow_log CREATE TABLE `slow_log` ( `user_host` mediumtext NOT NULL, `query_time` time(6) NOT NULL, `lock_time` time(6) NOT NULL, - `rows_sent` int(11) NOT NULL, - `rows_examined` int(11) NOT NULL, + `rows_sent` bigint(20) unsigned NOT NULL, + `rows_examined` bigint(20) unsigned NOT NULL, `db` varchar(512) NOT NULL, `last_insert_id` int(11) NOT NULL, `insert_id` int(11) NOT NULL, `server_id` int(10) unsigned NOT NULL, `sql_text` mediumtext NOT NULL, `thread_id` bigint(21) unsigned NOT NULL, - `rows_affected` int(11) NOT NULL + `rows_affected` bigint(20) unsigned NOT NULL ) ENGINE=CSV DEFAULT CHARSET=utf8mb3 COLLATE=utf8mb3_general_ci COMMENT='Slow log' show create table table_stats; Table Create Table diff --git a/mysql-test/main/system_mysql_db_fix50030.result b/mysql-test/main/system_mysql_db_fix50030.result index a257c16b865..c9594d494d6 100644 --- a/mysql-test/main/system_mysql_db_fix50030.result +++ b/mysql-test/main/system_mysql_db_fix50030.result @@ -99,6 +99,7 @@ db CREATE TABLE `db` ( `Event_priv` enum('N','Y') CHARACTER SET utf8mb3 COLLATE utf8mb3_general_ci NOT NULL DEFAULT 'N', `Trigger_priv` enum('N','Y') CHARACTER SET utf8mb3 COLLATE utf8mb3_general_ci NOT NULL DEFAULT 'N', `Delete_history_priv` enum('N','Y') CHARACTER SET utf8mb3 COLLATE utf8mb3_general_ci NOT NULL DEFAULT 'N', + `Show_create_routine_priv` enum('N','Y') CHARACTER SET utf8mb3 COLLATE utf8mb3_general_ci NOT NULL DEFAULT 'N', PRIMARY KEY (`Host`,`Db`,`User`), KEY `User` (`User`) ) ENGINE=Aria DEFAULT CHARSET=utf8mb3 COLLATE=utf8mb3_bin PAGE_CHECKSUM=1 TRANSACTIONAL=1 COMMENT='Database privileges' @@ -157,7 +158,7 @@ procs_priv CREATE TABLE `procs_priv` ( `Routine_name` char(64) CHARACTER SET utf8mb3 COLLATE utf8mb3_general_ci NOT NULL DEFAULT '', `Routine_type` enum('FUNCTION','PROCEDURE','PACKAGE','PACKAGE BODY') NOT NULL, `Grantor` varchar(384) NOT NULL DEFAULT '', - `Proc_priv` set('Execute','Alter Routine','Grant') CHARACTER SET utf8mb3 COLLATE utf8mb3_general_ci NOT NULL DEFAULT '', + `Proc_priv` set('Execute','Alter Routine','Grant','Show Create Routine') CHARACTER SET utf8mb3 COLLATE utf8mb3_general_ci NOT NULL DEFAULT '', `Timestamp` timestamp NOT NULL DEFAULT current_timestamp() ON UPDATE current_timestamp(), PRIMARY KEY (`Host`,`Db`,`User`,`Routine_name`,`Routine_type`), KEY `Grantor` (`Grantor`) @@ -246,15 +247,15 @@ slow_log CREATE TABLE `slow_log` ( `user_host` mediumtext NOT NULL, `query_time` time(6) NOT NULL, `lock_time` time(6) NOT NULL, - `rows_sent` int(11) NOT NULL, - `rows_examined` int(11) NOT NULL, + `rows_sent` bigint(20) unsigned NOT NULL, + `rows_examined` bigint(20) unsigned NOT NULL, `db` varchar(512) NOT NULL, `last_insert_id` int(11) NOT NULL, `insert_id` int(11) NOT NULL, `server_id` int(10) unsigned NOT NULL, `sql_text` mediumtext NOT NULL, `thread_id` bigint(21) unsigned NOT NULL, - `rows_affected` int(11) NOT NULL + `rows_affected` bigint(20) unsigned NOT NULL ) ENGINE=CSV DEFAULT CHARSET=utf8mb3 COLLATE=utf8mb3_general_ci COMMENT='Slow log' show create table table_stats; Table Create Table diff --git a/mysql-test/main/system_mysql_db_fix50117.result b/mysql-test/main/system_mysql_db_fix50117.result index fde130839d4..9057187a7a3 100644 --- a/mysql-test/main/system_mysql_db_fix50117.result +++ b/mysql-test/main/system_mysql_db_fix50117.result @@ -79,6 +79,7 @@ db CREATE TABLE `db` ( `Event_priv` enum('N','Y') CHARACTER SET utf8mb3 COLLATE utf8mb3_general_ci NOT NULL DEFAULT 'N', `Trigger_priv` enum('N','Y') CHARACTER SET utf8mb3 COLLATE utf8mb3_general_ci NOT NULL DEFAULT 'N', `Delete_history_priv` enum('N','Y') CHARACTER SET utf8mb3 COLLATE utf8mb3_general_ci NOT NULL DEFAULT 'N', + `Show_create_routine_priv` enum('N','Y') CHARACTER SET utf8mb3 COLLATE utf8mb3_general_ci NOT NULL DEFAULT 'N', PRIMARY KEY (`Host`,`Db`,`User`), KEY `User` (`User`) ) ENGINE=Aria DEFAULT CHARSET=utf8mb3 COLLATE=utf8mb3_bin PAGE_CHECKSUM=1 TRANSACTIONAL=1 COMMENT='Database privileges' @@ -137,7 +138,7 @@ procs_priv CREATE TABLE `procs_priv` ( `Routine_name` char(64) CHARACTER SET utf8mb3 COLLATE utf8mb3_general_ci NOT NULL DEFAULT '', `Routine_type` enum('FUNCTION','PROCEDURE','PACKAGE','PACKAGE BODY') NOT NULL, `Grantor` varchar(384) NOT NULL DEFAULT '', - `Proc_priv` set('Execute','Alter Routine','Grant') CHARACTER SET utf8mb3 COLLATE utf8mb3_general_ci NOT NULL DEFAULT '', + `Proc_priv` set('Execute','Alter Routine','Grant','Show Create Routine') CHARACTER SET utf8mb3 COLLATE utf8mb3_general_ci NOT NULL DEFAULT '', `Timestamp` timestamp NOT NULL DEFAULT current_timestamp() ON UPDATE current_timestamp(), PRIMARY KEY (`Host`,`Db`,`User`,`Routine_name`,`Routine_type`), KEY `Grantor` (`Grantor`) @@ -226,15 +227,15 @@ slow_log CREATE TABLE `slow_log` ( `user_host` mediumtext NOT NULL, `query_time` time(6) NOT NULL, `lock_time` time(6) NOT NULL, - `rows_sent` int(11) NOT NULL, - `rows_examined` int(11) NOT NULL, + `rows_sent` bigint(20) unsigned NOT NULL, + `rows_examined` bigint(20) unsigned NOT NULL, `db` varchar(512) NOT NULL, `last_insert_id` int(11) NOT NULL, `insert_id` int(11) NOT NULL, `server_id` int(10) unsigned NOT NULL, `sql_text` mediumtext NOT NULL, `thread_id` bigint(21) unsigned NOT NULL, - `rows_affected` int(11) NOT NULL + `rows_affected` bigint(20) unsigned NOT NULL ) ENGINE=CSV DEFAULT CHARSET=utf8mb3 COLLATE=utf8mb3_general_ci COMMENT='Slow log' show create table table_stats; Table Create Table diff --git a/mysql-test/main/system_mysql_db_fix50568.result b/mysql-test/main/system_mysql_db_fix50568.result index 763fcb866d0..561e7f7f4db 100644 --- a/mysql-test/main/system_mysql_db_fix50568.result +++ b/mysql-test/main/system_mysql_db_fix50568.result @@ -100,6 +100,7 @@ db CREATE TABLE `db` ( `Event_priv` enum('N','Y') CHARACTER SET utf8mb3 COLLATE utf8mb3_general_ci NOT NULL DEFAULT 'N', `Trigger_priv` enum('N','Y') CHARACTER SET utf8mb3 COLLATE utf8mb3_general_ci NOT NULL DEFAULT 'N', `Delete_history_priv` enum('N','Y') CHARACTER SET utf8mb3 COLLATE utf8mb3_general_ci NOT NULL DEFAULT 'N', + `Show_create_routine_priv` enum('N','Y') CHARACTER SET utf8mb3 COLLATE utf8mb3_general_ci NOT NULL DEFAULT 'N', PRIMARY KEY (`Host`,`Db`,`User`), KEY `User` (`User`) ) ENGINE=Aria DEFAULT CHARSET=utf8mb3 COLLATE=utf8mb3_bin PAGE_CHECKSUM=1 TRANSACTIONAL=1 COMMENT='Database privileges' @@ -158,7 +159,7 @@ procs_priv CREATE TABLE `procs_priv` ( `Routine_name` char(64) CHARACTER SET utf8mb3 COLLATE utf8mb3_general_ci NOT NULL DEFAULT '', `Routine_type` enum('FUNCTION','PROCEDURE','PACKAGE','PACKAGE BODY') NOT NULL, `Grantor` varchar(384) NOT NULL DEFAULT '', - `Proc_priv` set('Execute','Alter Routine','Grant') CHARACTER SET utf8mb3 COLLATE utf8mb3_general_ci NOT NULL DEFAULT '', + `Proc_priv` set('Execute','Alter Routine','Grant','Show Create Routine') CHARACTER SET utf8mb3 COLLATE utf8mb3_general_ci NOT NULL DEFAULT '', `Timestamp` timestamp NOT NULL DEFAULT current_timestamp() ON UPDATE current_timestamp(), PRIMARY KEY (`Host`,`Db`,`User`,`Routine_name`,`Routine_type`), KEY `Grantor` (`Grantor`) @@ -247,15 +248,15 @@ slow_log CREATE TABLE `slow_log` ( `user_host` mediumtext NOT NULL, `query_time` time(6) NOT NULL, `lock_time` time(6) NOT NULL, - `rows_sent` int(11) NOT NULL, - `rows_examined` int(11) NOT NULL, + `rows_sent` bigint(20) unsigned NOT NULL, + `rows_examined` bigint(20) unsigned NOT NULL, `db` varchar(512) NOT NULL, `last_insert_id` int(11) NOT NULL, `insert_id` int(11) NOT NULL, `server_id` int(10) unsigned NOT NULL, `sql_text` mediumtext NOT NULL, `thread_id` bigint(21) unsigned NOT NULL, - `rows_affected` int(11) NOT NULL + `rows_affected` bigint(20) unsigned NOT NULL ) ENGINE=CSV DEFAULT CHARSET=utf8mb3 COLLATE=utf8mb3_general_ci COMMENT='Slow log' show create table table_stats; Table Create Table diff --git a/mysql-test/main/table_elim.result b/mysql-test/main/table_elim.result index 580b1cf5a0d..34c27814106 100644 --- a/mysql-test/main/table_elim.result +++ b/mysql-test/main/table_elim.result @@ -250,11 +250,15 @@ explain select t1.* from t1 left join t2 on t2.a='foo' collate latin1_general_ci id select_type table type possible_keys key key_len ref rows Extra 1 SIMPLE t1 index NULL PRIMARY 10 NULL 2 Using index 1 SIMPLE t2 index PRIMARY PRIMARY 10 NULL 2 Using where; Using index +Warnings: +Note 1105 Cannot use key `PRIMARY` part[0] for lookup: `test`.`t2`.`a` of collation `latin1_general_cs` = "'foo' collate latin1_general_ci" of collation `latin1_general_ci` this must not use table elimination: explain select t1.* from t1 left join t2 on t2.a=t1.a collate latin1_general_ci; id select_type table type possible_keys key key_len ref rows Extra 1 SIMPLE t1 index NULL PRIMARY 10 NULL 2 Using index 1 SIMPLE t2 ALL PRIMARY NULL NULL NULL 2 Range checked for each record (index map: 0x1) +Warnings: +Note 1105 Cannot use key `PRIMARY` part[0] for lookup: `test`.`t2`.`a` of collation `latin1_general_cs` = "`t1`.`a` collate latin1_general_ci" of collation `latin1_general_ci` drop table t1,t2; create table t1 (a int primary key); insert into t1 values (1),(2); @@ -265,11 +269,15 @@ explain select t1.* from t1 left join t2 on t2.a=1; id select_type table type possible_keys key key_len ref rows Extra 1 SIMPLE t1 index NULL PRIMARY 4 NULL 2 Using index 1 SIMPLE t2 index PRIMARY PRIMARY 10 NULL 2 Using where; Using index +Warnings: +Note 1105 Cannot use key `PRIMARY` part[0] for lookup: `test`.`t2`.`a` of type `char` = "1" of type `int` this must not use table elimination: explain select t1.* from t1 left join t2 on t2.a=t1.a; id select_type table type possible_keys key key_len ref rows Extra 1 SIMPLE t1 index NULL PRIMARY 4 NULL 2 Using index 1 SIMPLE t2 ALL PRIMARY NULL NULL NULL 2 Range checked for each record (index map: 0x1) +Warnings: +Note 1105 Cannot use key `PRIMARY` part[0] for lookup: `test`.`t2`.`a` of type `char` = "`t1`.`a`" of type `int` drop table t1, t2; create table t1 (a char(10) primary key); insert into t1 values ('foo'),('bar'); diff --git a/mysql-test/main/timezone.result b/mysql-test/main/timezone.result index 2ba1e3fb1d5..2a099e90bad 100644 --- a/mysql-test/main/timezone.result +++ b/mysql-test/main/timezone.result @@ -75,3 +75,14 @@ alter table mysql.time_zone_transition_type add primary key (time_zone_id,transi # # End of 10.8 tests # +# +# MDEV-31684 Add timezone information to DATE_FORMAT +# +# using system time +SET @@time_zone= default; +SELECT DATE_FORMAT('2009-11-01 22:23:00', '%z %Z') AS current_timezone; +current_timezone ++0100 MET +SELECT DATE_FORMAT('2008-06-04 02:23:00', '%z %Z') AS current_timezone; +current_timezone ++0200 MEST diff --git a/mysql-test/main/timezone.test b/mysql-test/main/timezone.test index 89c3ab5cfc1..50e062b45f1 100644 --- a/mysql-test/main/timezone.test +++ b/mysql-test/main/timezone.test @@ -74,3 +74,12 @@ alter table mysql.time_zone_transition_type add primary key (time_zone_id,transi --echo # --echo # End of 10.8 tests --echo # + +--echo # +--echo # MDEV-31684 Add timezone information to DATE_FORMAT +--echo # + +--echo # using system time +SET @@time_zone= default; +SELECT DATE_FORMAT('2009-11-01 22:23:00', '%z %Z') AS current_timezone; +SELECT DATE_FORMAT('2008-06-04 02:23:00', '%z %Z') AS current_timezone; diff --git a/mysql-test/main/tls_version.result b/mysql-test/main/tls_version.result index d1b20a121fe..3d9565983e8 100644 --- a/mysql-test/main/tls_version.result +++ b/mysql-test/main/tls_version.result @@ -12,3 +12,5 @@ Variable_name Value Ssl_version TLSv1.2 @@tls_version TLSv1.1,TLSv1.2 +call mtr.add_suppression("TLSv1.0 and TLSv1.1 are insecure"); +FOUND 1 /TLSv1.0 and TLSv1.1 are insecure/ in mysqld.1.err diff --git a/mysql-test/main/tls_version.test b/mysql-test/main/tls_version.test index 875fed19821..50448f898e9 100644 --- a/mysql-test/main/tls_version.test +++ b/mysql-test/main/tls_version.test @@ -22,3 +22,8 @@ # finally list available protocols --exec $MYSQL --host=localhost --ssl -e "select @@tls_version;" +call mtr.add_suppression("TLSv1.0 and TLSv1.1 are insecure"); +--let SEARCH_FILE=$MYSQLTEST_VARDIR/log/mysqld.1.err +--let SEARCH_PATTERN= TLSv1.0 and TLSv1.1 are insecure +--source include/search_pattern_in_file.inc + diff --git a/mysql-test/main/tls_version1.result b/mysql-test/main/tls_version1.result index 8333bfec159..caabed832cb 100644 --- a/mysql-test/main/tls_version1.result +++ b/mysql-test/main/tls_version1.result @@ -4,3 +4,5 @@ Variable_name Value Ssl_version TLSv1 @@tls_version TLSv1.0 +call mtr.add_suppression("TLSv1.0 and TLSv1.1 are insecure"); +FOUND 1 /TLSv1.0 and TLSv1.1 are insecure/ in mysqld.1.err diff --git a/mysql-test/main/tls_version1.test b/mysql-test/main/tls_version1.test index d38de876ba3..788284c36df 100644 --- a/mysql-test/main/tls_version1.test +++ b/mysql-test/main/tls_version1.test @@ -10,3 +10,8 @@ --exec $MYSQL --host=localhost --ssl --tls_version=TLSv1.0 -e "show status like 'ssl_version';" --exec $MYSQL --host=localhost --ssl -e "select @@tls_version;" +call mtr.add_suppression("TLSv1.0 and TLSv1.1 are insecure"); +--let SEARCH_FILE=$MYSQLTEST_VARDIR/log/mysqld.1.err +--let SEARCH_PATTERN= TLSv1.0 and TLSv1.1 are insecure +--source include/search_pattern_in_file.inc + diff --git a/mysql-test/main/type_binary.result b/mysql-test/main/type_binary.result index ca0495e3899..d1aa4ada5af 100644 --- a/mysql-test/main/type_binary.result +++ b/mysql-test/main/type_binary.result @@ -220,3 +220,180 @@ def CAST(a AS BINARY(16777215)) 250 16777215 0 Y 128 0 63 def CAST(a AS BINARY(16777216)) 251 16777216 0 Y 128 0 63 CAST(a AS BINARY(0)) CAST(a AS BINARY(1)) CAST(a AS BINARY(16)) CAST(a AS BINARY(255)) CAST(a AS BINARY(256)) CAST(a AS BINARY(512)) CAST(a AS BINARY(513)) CAST(a AS BINARY(65532)) CAST(a AS BINARY(65533)) CAST(a AS BINARY(65534)) CAST(a AS BINARY(65535)) CAST(a AS BINARY(65536)) CAST(a AS BINARY(16777215)) CAST(a AS BINARY(16777216)) DROP TABLE t1; +# +# MDEV-32203 Raise notes when an index cannot be used on data type mismatch +# +SET note_verbosity=unusable_keys; +CREATE TABLE t1 (indexed_col VARBINARY(32), KEY(indexed_col)); +FOR i IN 1..31 +DO +INSERT INTO t1 VALUES (20230100+i); +END FOR; +$$ +SELECT * FROM t1 WHERE indexed_col=20230101; +indexed_col +20230101 +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `varchar` = "20230101" of type `int` +SELECT * FROM t1 WHERE indexed_col=20230101102030; +indexed_col +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `varchar` = "20230101102030" of type `bigint` +SELECT * FROM t1 WHERE indexed_col=20230101102030.1; +indexed_col +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `varchar` = "20230101102030.1" of type `decimal` +SELECT * FROM t1 WHERE indexed_col=20230101102030.1e0; +indexed_col +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `varchar` = "20230101102030.1e0" of type `double` +SELECT * FROM t1 WHERE indexed_col='10:20:30'; +indexed_col +SELECT * FROM t1 WHERE indexed_col='2001-01-01'; +indexed_col +SELECT * FROM t1 WHERE indexed_col='2001-01-01 10:20:30'; +indexed_col +SELECT * FROM t1 WHERE indexed_col=DATE'2001-01-01'; +indexed_col +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `varchar` = "DATE'2001-01-01'" of type `date` +SELECT * FROM t1 WHERE indexed_col=TIME'10:20:30'; +indexed_col +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `varchar` = "TIME'10:20:30'" of type `time` +Warning 1292 Truncated incorrect time value: '20230101' +Warning 1292 Truncated incorrect time value: '20230102' +Warning 1292 Truncated incorrect time value: '20230103' +Warning 1292 Truncated incorrect time value: '20230104' +Warning 1292 Truncated incorrect time value: '20230105' +Warning 1292 Truncated incorrect time value: '20230106' +Warning 1292 Truncated incorrect time value: '20230107' +Warning 1292 Truncated incorrect time value: '20230108' +Warning 1292 Truncated incorrect time value: '20230109' +Warning 1292 Truncated incorrect time value: '20230110' +Warning 1292 Truncated incorrect time value: '20230111' +Warning 1292 Truncated incorrect time value: '20230112' +Warning 1292 Truncated incorrect time value: '20230113' +Warning 1292 Truncated incorrect time value: '20230114' +Warning 1292 Truncated incorrect time value: '20230115' +Warning 1292 Truncated incorrect time value: '20230116' +Warning 1292 Truncated incorrect time value: '20230117' +Warning 1292 Truncated incorrect time value: '20230118' +Warning 1292 Truncated incorrect time value: '20230119' +Warning 1292 Truncated incorrect time value: '20230120' +Warning 1292 Truncated incorrect time value: '20230121' +Warning 1292 Truncated incorrect time value: '20230122' +Warning 1292 Truncated incorrect time value: '20230123' +Warning 1292 Truncated incorrect time value: '20230124' +Warning 1292 Truncated incorrect time value: '20230125' +Warning 1292 Truncated incorrect time value: '20230126' +Warning 1292 Truncated incorrect time value: '20230127' +Warning 1292 Truncated incorrect time value: '20230128' +Warning 1292 Truncated incorrect time value: '20230129' +Warning 1292 Truncated incorrect time value: '20230130' +Warning 1292 Truncated incorrect time value: '20230131' +SELECT * FROM t1 WHERE indexed_col=TIMESTAMP'2001-01-01 10:20:30'; +indexed_col +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `varchar` = "TIMESTAMP'2001-01-01 10:20:30'" of type `datetime` +SELECT * FROM t1 WHERE indexed_col=0x00; +indexed_col +SELECT * FROM t1 WHERE indexed_col=_utf8mb3'0' COLLATE utf8mb3_bin; +indexed_col +Warnings: +Note 1105 Cannot use key parts with `test`.`t1`.`indexed_col` in the rewritten condition: `convert(``t1``.``indexed_col`` using utf8mb3) = _utf8mb3'0' collate utf8mb3_bin` +CREATE TABLE t2 (not_indexed_col INT); +INSERT INTO t2 VALUES (20230101),(20230102); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +20230101 20230101 +20230102 20230102 +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `varchar` = "`t2`.`not_indexed_col`" of type `int` +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col INT UNSIGNED); +INSERT INTO t2 VALUES (20230101),(20230102); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +20230101 20230101 +20230102 20230102 +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `varchar` = "`t2`.`not_indexed_col`" of type `int unsigned` +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col BIGINT); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `varchar` = "`t2`.`not_indexed_col`" of type `bigint` +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col BIGINT UNSIGNED); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `varchar` = "`t2`.`not_indexed_col`" of type `bigint unsigned` +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col DECIMAL(30,6)); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `varchar` = "`t2`.`not_indexed_col`" of type `decimal` +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col FLOAT); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `varchar` = "`t2`.`not_indexed_col`" of type `float` +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col DOUBLE); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `varchar` = "`t2`.`not_indexed_col`" of type `double` +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col DATE); +INSERT INTO t2 VALUES ('2023-01-01'),('2023-01-02'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +20230101 2023-01-01 +20230102 2023-01-02 +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `varchar` = "`t2`.`not_indexed_col`" of type `date` +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col DATETIME); +INSERT INTO t2 VALUES ('2023-01-01 00:00:00'),('2023-01-01 00:00:01'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +20230101 2023-01-01 00:00:00 +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `varchar` = "`t2`.`not_indexed_col`" of type `datetime` +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col TIMESTAMP); +INSERT INTO t2 VALUES ('2023-01-01 00:00:00'),('2023-01-01 00:00:01'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +20230101 2023-01-01 00:00:00 +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `varchar` = "`t2`.`not_indexed_col`" of type `timestamp` +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col VARBINARY(32)); +INSERT INTO t2 VALUES (0x30),(0x31); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col VARCHAR(32)); +INSERT INTO t2 VALUES ('2001-01-01'),('2001-01-02'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col VARCHAR(32) CHARACTER SET utf8mb3); +INSERT INTO t2 VALUES ('2001-01-01'),('2001-01-02'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +DROP TABLE t1; +SET note_verbosity=DEFAULT; diff --git a/mysql-test/main/type_binary.test b/mysql-test/main/type_binary.test index 04cdc94e6d8..bfc9222762a 100644 --- a/mysql-test/main/type_binary.test +++ b/mysql-test/main/type_binary.test @@ -156,3 +156,22 @@ FROM t1; --disable_metadata --enable_view_protocol DROP TABLE t1; + + +--echo # +--echo # MDEV-32203 Raise notes when an index cannot be used on data type mismatch +--echo # + +SET note_verbosity=unusable_keys; +CREATE TABLE t1 (indexed_col VARBINARY(32), KEY(indexed_col)); +DELIMITER $$; +FOR i IN 1..31 +DO + INSERT INTO t1 VALUES (20230100+i); +END FOR; +$$ +DELIMITER ;$$ +--source unusable_keys_literals.inc +--source unusable_keys_joins.inc +DROP TABLE t1; +SET note_verbosity=DEFAULT; diff --git a/mysql-test/main/type_bit.result b/mysql-test/main/type_bit.result index e051a52d56a..d075e883ac2 100644 --- a/mysql-test/main/type_bit.result +++ b/mysql-test/main/type_bit.result @@ -1884,3 +1884,157 @@ DROP TABLE t1; # # End of 10.5 tests # +# +# MDEV-32203 Raise notes when an index cannot be used on data type mismatch +# +SET note_verbosity=unusable_keys; +CREATE TABLE t1 (indexed_col BIT(64), KEY(indexed_col)); +FOR i IN 1..31 +DO +INSERT INTO t1 VALUES (CONCAT(20230100+i)); +END FOR; +$$ +SELECT * FROM t1 WHERE indexed_col=20230101; +indexed_col +SELECT * FROM t1 WHERE indexed_col=20230101102030; +indexed_col +SELECT * FROM t1 WHERE indexed_col=20230101102030.1; +indexed_col +SELECT * FROM t1 WHERE indexed_col=20230101102030.1e0; +indexed_col +SELECT * FROM t1 WHERE indexed_col='10:20:30'; +indexed_col +SELECT * FROM t1 WHERE indexed_col='2001-01-01'; +indexed_col +SELECT * FROM t1 WHERE indexed_col='2001-01-01 10:20:30'; +indexed_col +SELECT * FROM t1 WHERE indexed_col=DATE'2001-01-01'; +indexed_col +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `bit` = "DATE'2001-01-01'" of type `date` +SELECT * FROM t1 WHERE indexed_col=TIME'10:20:30'; +indexed_col +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `bit` = "TIME'10:20:30'" of type `time` +Warning 1292 Truncated incorrect time value: '20230101' +Warning 1292 Truncated incorrect time value: '20230102' +Warning 1292 Truncated incorrect time value: '20230103' +Warning 1292 Truncated incorrect time value: '20230104' +Warning 1292 Truncated incorrect time value: '20230105' +Warning 1292 Truncated incorrect time value: '20230106' +Warning 1292 Truncated incorrect time value: '20230107' +Warning 1292 Truncated incorrect time value: '20230108' +Warning 1292 Truncated incorrect time value: '20230109' +Warning 1292 Truncated incorrect time value: '20230110' +Warning 1292 Truncated incorrect time value: '20230111' +Warning 1292 Truncated incorrect time value: '20230112' +Warning 1292 Truncated incorrect time value: '20230113' +Warning 1292 Truncated incorrect time value: '20230114' +Warning 1292 Truncated incorrect time value: '20230115' +Warning 1292 Truncated incorrect time value: '20230116' +Warning 1292 Truncated incorrect time value: '20230117' +Warning 1292 Truncated incorrect time value: '20230118' +Warning 1292 Truncated incorrect time value: '20230119' +Warning 1292 Truncated incorrect time value: '20230120' +Warning 1292 Truncated incorrect time value: '20230121' +Warning 1292 Truncated incorrect time value: '20230122' +Warning 1292 Truncated incorrect time value: '20230123' +Warning 1292 Truncated incorrect time value: '20230124' +Warning 1292 Truncated incorrect time value: '20230125' +Warning 1292 Truncated incorrect time value: '20230126' +Warning 1292 Truncated incorrect time value: '20230127' +Warning 1292 Truncated incorrect time value: '20230128' +Warning 1292 Truncated incorrect time value: '20230129' +Warning 1292 Truncated incorrect time value: '20230130' +Warning 1292 Truncated incorrect time value: '20230131' +SELECT * FROM t1 WHERE indexed_col=TIMESTAMP'2001-01-01 10:20:30'; +indexed_col +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `bit` = "TIMESTAMP'2001-01-01 10:20:30'" of type `datetime` +SELECT * FROM t1 WHERE indexed_col=0x00; +indexed_col +SELECT * FROM t1 WHERE indexed_col=_utf8mb3'0' COLLATE utf8mb3_bin; +indexed_col +CREATE TABLE t2 (not_indexed_col INT); +INSERT INTO t2 VALUES (20230101),(20230102); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col INT UNSIGNED); +INSERT INTO t2 VALUES (20230101),(20230102); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col BIGINT); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col BIGINT UNSIGNED); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col DECIMAL(30,6)); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col FLOAT); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col DOUBLE); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col DATE); +INSERT INTO t2 VALUES ('2023-01-01'),('2023-01-02'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +20230101 2023-01-01 +20230102 2023-01-02 +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `bit` = "`t2`.`not_indexed_col`" of type `date` +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col DATETIME); +INSERT INTO t2 VALUES ('2023-01-01 00:00:00'),('2023-01-01 00:00:01'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +20230101 2023-01-01 00:00:00 +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `bit` = "`t2`.`not_indexed_col`" of type `datetime` +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col TIMESTAMP); +INSERT INTO t2 VALUES ('2023-01-01 00:00:00'),('2023-01-01 00:00:01'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +20230101 2023-01-01 00:00:00 +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `bit` = "`t2`.`not_indexed_col`" of type `timestamp` +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col VARBINARY(32)); +INSERT INTO t2 VALUES (0x30),(0x31); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col VARCHAR(32)); +INSERT INTO t2 VALUES ('2001-01-01'),('2001-01-02'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +Warnings: +Warning 1292 Truncated incorrect INTEGER value: '2001-01-01' +Warning 1292 Truncated incorrect INTEGER value: '2001-01-02' +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col VARCHAR(32) CHARACTER SET utf8mb3); +INSERT INTO t2 VALUES ('2001-01-01'),('2001-01-02'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +Warnings: +Warning 1292 Truncated incorrect INTEGER value: '2001-01-01' +Warning 1292 Truncated incorrect INTEGER value: '2001-01-02' +DROP TABLE t2; +DROP TABLE t1; +SET note_verbosity=DEFAULT; diff --git a/mysql-test/main/type_bit.test b/mysql-test/main/type_bit.test index 846fc34e2e9..8bab78adeaf 100644 --- a/mysql-test/main/type_bit.test +++ b/mysql-test/main/type_bit.test @@ -571,3 +571,22 @@ DROP TABLE t1; --echo # --echo # End of 10.5 tests --echo # + + +--echo # +--echo # MDEV-32203 Raise notes when an index cannot be used on data type mismatch +--echo # + +SET note_verbosity=unusable_keys; +CREATE TABLE t1 (indexed_col BIT(64), KEY(indexed_col)); +DELIMITER $$; +FOR i IN 1..31 +DO + INSERT INTO t1 VALUES (CONCAT(20230100+i)); +END FOR; +$$ +DELIMITER ;$$ +--source unusable_keys_literals.inc +--source unusable_keys_joins.inc +DROP TABLE t1; +SET note_verbosity=DEFAULT; diff --git a/mysql-test/main/type_bit_innodb.result b/mysql-test/main/type_bit_innodb.result index 67b4ff55674..fc932c8749e 100644 --- a/mysql-test/main/type_bit_innodb.result +++ b/mysql-test/main/type_bit_innodb.result @@ -424,3 +424,157 @@ hex(f1) hex(f2) 0 0 drop table t1; SET GLOBAL innodb_stats_persistent=@save_stats_persistent; +# +# MDEV-32203 Raise notes when an index cannot be used on data type mismatch +# +SET note_verbosity=unusable_keys; +CREATE TABLE t1 (indexed_col BIT(64), KEY(indexed_col)) ENGINE=InnoDB; +FOR i IN 1..31 +DO +INSERT INTO t1 VALUES (CONCAT(20230100+i)); +END FOR; +$$ +SELECT * FROM t1 WHERE indexed_col=20230101; +indexed_col +SELECT * FROM t1 WHERE indexed_col=20230101102030; +indexed_col +SELECT * FROM t1 WHERE indexed_col=20230101102030.1; +indexed_col +SELECT * FROM t1 WHERE indexed_col=20230101102030.1e0; +indexed_col +SELECT * FROM t1 WHERE indexed_col='10:20:30'; +indexed_col +SELECT * FROM t1 WHERE indexed_col='2001-01-01'; +indexed_col +SELECT * FROM t1 WHERE indexed_col='2001-01-01 10:20:30'; +indexed_col +SELECT * FROM t1 WHERE indexed_col=DATE'2001-01-01'; +indexed_col +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `bit` = "DATE'2001-01-01'" of type `date` +SELECT * FROM t1 WHERE indexed_col=TIME'10:20:30'; +indexed_col +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `bit` = "TIME'10:20:30'" of type `time` +Warning 1292 Truncated incorrect time value: '20230101' +Warning 1292 Truncated incorrect time value: '20230102' +Warning 1292 Truncated incorrect time value: '20230103' +Warning 1292 Truncated incorrect time value: '20230104' +Warning 1292 Truncated incorrect time value: '20230105' +Warning 1292 Truncated incorrect time value: '20230106' +Warning 1292 Truncated incorrect time value: '20230107' +Warning 1292 Truncated incorrect time value: '20230108' +Warning 1292 Truncated incorrect time value: '20230109' +Warning 1292 Truncated incorrect time value: '20230110' +Warning 1292 Truncated incorrect time value: '20230111' +Warning 1292 Truncated incorrect time value: '20230112' +Warning 1292 Truncated incorrect time value: '20230113' +Warning 1292 Truncated incorrect time value: '20230114' +Warning 1292 Truncated incorrect time value: '20230115' +Warning 1292 Truncated incorrect time value: '20230116' +Warning 1292 Truncated incorrect time value: '20230117' +Warning 1292 Truncated incorrect time value: '20230118' +Warning 1292 Truncated incorrect time value: '20230119' +Warning 1292 Truncated incorrect time value: '20230120' +Warning 1292 Truncated incorrect time value: '20230121' +Warning 1292 Truncated incorrect time value: '20230122' +Warning 1292 Truncated incorrect time value: '20230123' +Warning 1292 Truncated incorrect time value: '20230124' +Warning 1292 Truncated incorrect time value: '20230125' +Warning 1292 Truncated incorrect time value: '20230126' +Warning 1292 Truncated incorrect time value: '20230127' +Warning 1292 Truncated incorrect time value: '20230128' +Warning 1292 Truncated incorrect time value: '20230129' +Warning 1292 Truncated incorrect time value: '20230130' +Warning 1292 Truncated incorrect time value: '20230131' +SELECT * FROM t1 WHERE indexed_col=TIMESTAMP'2001-01-01 10:20:30'; +indexed_col +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `bit` = "TIMESTAMP'2001-01-01 10:20:30'" of type `datetime` +SELECT * FROM t1 WHERE indexed_col=0x00; +indexed_col +SELECT * FROM t1 WHERE indexed_col=_utf8mb3'0' COLLATE utf8mb3_bin; +indexed_col +CREATE TABLE t2 (not_indexed_col INT); +INSERT INTO t2 VALUES (20230101),(20230102); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col INT UNSIGNED); +INSERT INTO t2 VALUES (20230101),(20230102); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col BIGINT); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col BIGINT UNSIGNED); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col DECIMAL(30,6)); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col FLOAT); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col DOUBLE); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col DATE); +INSERT INTO t2 VALUES ('2023-01-01'),('2023-01-02'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +20230101 2023-01-01 +20230102 2023-01-02 +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `bit` = "`t2`.`not_indexed_col`" of type `date` +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col DATETIME); +INSERT INTO t2 VALUES ('2023-01-01 00:00:00'),('2023-01-01 00:00:01'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +20230101 2023-01-01 00:00:00 +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `bit` = "`t2`.`not_indexed_col`" of type `datetime` +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col TIMESTAMP); +INSERT INTO t2 VALUES ('2023-01-01 00:00:00'),('2023-01-01 00:00:01'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +20230101 2023-01-01 00:00:00 +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `bit` = "`t2`.`not_indexed_col`" of type `timestamp` +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col VARBINARY(32)); +INSERT INTO t2 VALUES (0x30),(0x31); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col VARCHAR(32)); +INSERT INTO t2 VALUES ('2001-01-01'),('2001-01-02'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +Warnings: +Warning 1292 Truncated incorrect INTEGER value: '2001-01-01' +Warning 1292 Truncated incorrect INTEGER value: '2001-01-02' +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col VARCHAR(32) CHARACTER SET utf8mb3); +INSERT INTO t2 VALUES ('2001-01-01'),('2001-01-02'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +Warnings: +Warning 1292 Truncated incorrect INTEGER value: '2001-01-01' +Warning 1292 Truncated incorrect INTEGER value: '2001-01-02' +DROP TABLE t2; +DROP TABLE t1; +SET note_verbosity=DEFAULT; diff --git a/mysql-test/main/type_bit_innodb.test b/mysql-test/main/type_bit_innodb.test index 5fc7c188246..196f28f12ec 100644 --- a/mysql-test/main/type_bit_innodb.test +++ b/mysql-test/main/type_bit_innodb.test @@ -160,3 +160,21 @@ select hex(f1), hex(f2) from t1; drop table t1; SET GLOBAL innodb_stats_persistent=@save_stats_persistent; + +--echo # +--echo # MDEV-32203 Raise notes when an index cannot be used on data type mismatch +--echo # + +SET note_verbosity=unusable_keys; +CREATE TABLE t1 (indexed_col BIT(64), KEY(indexed_col)) ENGINE=InnoDB; +DELIMITER $$; +FOR i IN 1..31 +DO + INSERT INTO t1 VALUES (CONCAT(20230100+i)); +END FOR; +$$ +DELIMITER ;$$ +--source unusable_keys_literals.inc +--source unusable_keys_joins.inc +DROP TABLE t1; +SET note_verbosity=DEFAULT; diff --git a/mysql-test/main/type_blob.result b/mysql-test/main/type_blob.result index 38b7bd30ff9..bc25af5af90 100644 --- a/mysql-test/main/type_blob.result +++ b/mysql-test/main/type_blob.result @@ -1159,3 +1159,263 @@ drop table t1; # # End of 10.4 test # +# +# MDEV-32203 Raise notes when an index cannot be used on data type mismatch +# +SET note_verbosity=unusable_keys; +CREATE TABLE t1 (indexed_col BLOB, KEY(indexed_col(64))); +FOR i IN 1..31 +DO +INSERT INTO t1 VALUES (20230100+i); +END FOR; +$$ +SELECT * FROM t1 WHERE indexed_col=20230101; +indexed_col +20230101 +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `blob` = "20230101" of type `int` +SELECT * FROM t1 WHERE indexed_col=20230101102030; +indexed_col +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `blob` = "20230101102030" of type `bigint` +SELECT * FROM t1 WHERE indexed_col=20230101102030.1; +indexed_col +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `blob` = "20230101102030.1" of type `decimal` +SELECT * FROM t1 WHERE indexed_col=20230101102030.1e0; +indexed_col +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `blob` = "20230101102030.1e0" of type `double` +SELECT * FROM t1 WHERE indexed_col='10:20:30'; +indexed_col +SELECT * FROM t1 WHERE indexed_col='2001-01-01'; +indexed_col +SELECT * FROM t1 WHERE indexed_col='2001-01-01 10:20:30'; +indexed_col +SELECT * FROM t1 WHERE indexed_col=DATE'2001-01-01'; +indexed_col +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `blob` = "DATE'2001-01-01'" of type `date` +SELECT * FROM t1 WHERE indexed_col=TIME'10:20:30'; +indexed_col +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `blob` = "TIME'10:20:30'" of type `time` +Warning 1292 Truncated incorrect time value: '20230101' +Warning 1292 Truncated incorrect time value: '20230102' +Warning 1292 Truncated incorrect time value: '20230103' +Warning 1292 Truncated incorrect time value: '20230104' +Warning 1292 Truncated incorrect time value: '20230105' +Warning 1292 Truncated incorrect time value: '20230106' +Warning 1292 Truncated incorrect time value: '20230107' +Warning 1292 Truncated incorrect time value: '20230108' +Warning 1292 Truncated incorrect time value: '20230109' +Warning 1292 Truncated incorrect time value: '20230110' +Warning 1292 Truncated incorrect time value: '20230111' +Warning 1292 Truncated incorrect time value: '20230112' +Warning 1292 Truncated incorrect time value: '20230113' +Warning 1292 Truncated incorrect time value: '20230114' +Warning 1292 Truncated incorrect time value: '20230115' +Warning 1292 Truncated incorrect time value: '20230116' +Warning 1292 Truncated incorrect time value: '20230117' +Warning 1292 Truncated incorrect time value: '20230118' +Warning 1292 Truncated incorrect time value: '20230119' +Warning 1292 Truncated incorrect time value: '20230120' +Warning 1292 Truncated incorrect time value: '20230121' +Warning 1292 Truncated incorrect time value: '20230122' +Warning 1292 Truncated incorrect time value: '20230123' +Warning 1292 Truncated incorrect time value: '20230124' +Warning 1292 Truncated incorrect time value: '20230125' +Warning 1292 Truncated incorrect time value: '20230126' +Warning 1292 Truncated incorrect time value: '20230127' +Warning 1292 Truncated incorrect time value: '20230128' +Warning 1292 Truncated incorrect time value: '20230129' +Warning 1292 Truncated incorrect time value: '20230130' +Warning 1292 Truncated incorrect time value: '20230131' +SELECT * FROM t1 WHERE indexed_col=TIMESTAMP'2001-01-01 10:20:30'; +indexed_col +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `blob` = "TIMESTAMP'2001-01-01 10:20:30'" of type `datetime` +SELECT * FROM t1 WHERE indexed_col=0x00; +indexed_col +SELECT * FROM t1 WHERE indexed_col=_utf8mb3'0' COLLATE utf8mb3_bin; +indexed_col +Warnings: +Note 1105 Cannot use key parts with `test`.`t1`.`indexed_col` in the rewritten condition: `convert(``t1``.``indexed_col`` using utf8mb3) = _utf8mb3'0' collate utf8mb3_bin` +DROP TABLE t1; +SET note_verbosity=DEFAULT; +SET note_verbosity=unusable_keys; +CREATE TABLE t1 (indexed_col TEXT, KEY(indexed_col(64))); +FOR i IN 1..31 +DO +INSERT INTO t1 VALUES (20230100+i); +END FOR; +$$ +SELECT * FROM t1 WHERE indexed_col=20230101; +indexed_col +20230101 +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `blob` = "20230101" of type `int` +SELECT * FROM t1 WHERE indexed_col=20230101102030; +indexed_col +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `blob` = "20230101102030" of type `bigint` +SELECT * FROM t1 WHERE indexed_col=20230101102030.1; +indexed_col +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `blob` = "20230101102030.1" of type `decimal` +SELECT * FROM t1 WHERE indexed_col=20230101102030.1e0; +indexed_col +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `blob` = "20230101102030.1e0" of type `double` +SELECT * FROM t1 WHERE indexed_col='10:20:30'; +indexed_col +SELECT * FROM t1 WHERE indexed_col='2001-01-01'; +indexed_col +SELECT * FROM t1 WHERE indexed_col='2001-01-01 10:20:30'; +indexed_col +SELECT * FROM t1 WHERE indexed_col=DATE'2001-01-01'; +indexed_col +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `blob` = "DATE'2001-01-01'" of type `date` +SELECT * FROM t1 WHERE indexed_col=TIME'10:20:30'; +indexed_col +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `blob` = "TIME'10:20:30'" of type `time` +Warning 1292 Truncated incorrect time value: '20230101' +Warning 1292 Truncated incorrect time value: '20230102' +Warning 1292 Truncated incorrect time value: '20230103' +Warning 1292 Truncated incorrect time value: '20230104' +Warning 1292 Truncated incorrect time value: '20230105' +Warning 1292 Truncated incorrect time value: '20230106' +Warning 1292 Truncated incorrect time value: '20230107' +Warning 1292 Truncated incorrect time value: '20230108' +Warning 1292 Truncated incorrect time value: '20230109' +Warning 1292 Truncated incorrect time value: '20230110' +Warning 1292 Truncated incorrect time value: '20230111' +Warning 1292 Truncated incorrect time value: '20230112' +Warning 1292 Truncated incorrect time value: '20230113' +Warning 1292 Truncated incorrect time value: '20230114' +Warning 1292 Truncated incorrect time value: '20230115' +Warning 1292 Truncated incorrect time value: '20230116' +Warning 1292 Truncated incorrect time value: '20230117' +Warning 1292 Truncated incorrect time value: '20230118' +Warning 1292 Truncated incorrect time value: '20230119' +Warning 1292 Truncated incorrect time value: '20230120' +Warning 1292 Truncated incorrect time value: '20230121' +Warning 1292 Truncated incorrect time value: '20230122' +Warning 1292 Truncated incorrect time value: '20230123' +Warning 1292 Truncated incorrect time value: '20230124' +Warning 1292 Truncated incorrect time value: '20230125' +Warning 1292 Truncated incorrect time value: '20230126' +Warning 1292 Truncated incorrect time value: '20230127' +Warning 1292 Truncated incorrect time value: '20230128' +Warning 1292 Truncated incorrect time value: '20230129' +Warning 1292 Truncated incorrect time value: '20230130' +Warning 1292 Truncated incorrect time value: '20230131' +SELECT * FROM t1 WHERE indexed_col=TIMESTAMP'2001-01-01 10:20:30'; +indexed_col +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `blob` = "TIMESTAMP'2001-01-01 10:20:30'" of type `datetime` +SELECT * FROM t1 WHERE indexed_col=0x00; +indexed_col +SELECT * FROM t1 WHERE indexed_col=_utf8mb3'0' COLLATE utf8mb3_bin; +indexed_col +Warnings: +Note 1105 Cannot use key parts with `test`.`t1`.`indexed_col` in the rewritten condition: `convert(``t1``.``indexed_col`` using utf8mb3) = _utf8mb3'0' collate utf8mb3_bin` +CREATE TABLE t2 (not_indexed_col INT); +INSERT INTO t2 VALUES (20230101),(20230102); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +20230101 20230101 +20230102 20230102 +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `blob` = "`t2`.`not_indexed_col`" of type `int` +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col INT UNSIGNED); +INSERT INTO t2 VALUES (20230101),(20230102); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +20230101 20230101 +20230102 20230102 +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `blob` = "`t2`.`not_indexed_col`" of type `int unsigned` +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col BIGINT); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `blob` = "`t2`.`not_indexed_col`" of type `bigint` +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col BIGINT UNSIGNED); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `blob` = "`t2`.`not_indexed_col`" of type `bigint unsigned` +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col DECIMAL(30,6)); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `blob` = "`t2`.`not_indexed_col`" of type `decimal` +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col FLOAT); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `blob` = "`t2`.`not_indexed_col`" of type `float` +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col DOUBLE); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `blob` = "`t2`.`not_indexed_col`" of type `double` +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col DATE); +INSERT INTO t2 VALUES ('2023-01-01'),('2023-01-02'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +20230101 2023-01-01 +20230102 2023-01-02 +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `blob` = "`t2`.`not_indexed_col`" of type `date` +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col DATETIME); +INSERT INTO t2 VALUES ('2023-01-01 00:00:00'),('2023-01-01 00:00:01'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +20230101 2023-01-01 00:00:00 +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `blob` = "`t2`.`not_indexed_col`" of type `datetime` +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col TIMESTAMP); +INSERT INTO t2 VALUES ('2023-01-01 00:00:00'),('2023-01-01 00:00:01'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +20230101 2023-01-01 00:00:00 +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `blob` = "`t2`.`not_indexed_col`" of type `timestamp` +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col VARBINARY(32)); +INSERT INTO t2 VALUES (0x30),(0x31); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col VARCHAR(32)); +INSERT INTO t2 VALUES ('2001-01-01'),('2001-01-02'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col VARCHAR(32) CHARACTER SET utf8mb3); +INSERT INTO t2 VALUES ('2001-01-01'),('2001-01-02'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +Warnings: +Note 1105 Cannot use key parts with `test`.`t1`.`indexed_col` in the rewritten condition: `convert(``t1``.``indexed_col`` using utf8mb3) = ``t2``.``not_indexed_col``` +DROP TABLE t2; +DROP TABLE t1; +SET note_verbosity=DEFAULT; diff --git a/mysql-test/main/type_blob.test b/mysql-test/main/type_blob.test index 021ead2e87c..ad58946afea 100644 --- a/mysql-test/main/type_blob.test +++ b/mysql-test/main/type_blob.test @@ -777,3 +777,34 @@ drop table t1; --echo # --echo # End of 10.4 test --echo # + +--echo # +--echo # MDEV-32203 Raise notes when an index cannot be used on data type mismatch +--echo # + +SET note_verbosity=unusable_keys; +CREATE TABLE t1 (indexed_col BLOB, KEY(indexed_col(64))); +DELIMITER $$; +FOR i IN 1..31 +DO + INSERT INTO t1 VALUES (20230100+i); +END FOR; +$$ +DELIMITER ;$$ +--source unusable_keys_literals.inc +DROP TABLE t1; +SET note_verbosity=DEFAULT; + +SET note_verbosity=unusable_keys; +CREATE TABLE t1 (indexed_col TEXT, KEY(indexed_col(64))); +DELIMITER $$; +FOR i IN 1..31 +DO + INSERT INTO t1 VALUES (20230100+i); +END FOR; +$$ +DELIMITER ;$$ +--source unusable_keys_literals.inc +--source unusable_keys_joins.inc +DROP TABLE t1; +SET note_verbosity=DEFAULT; diff --git a/mysql-test/main/type_date.result b/mysql-test/main/type_date.result index feac3295faf..b5cd3bf3b61 100644 --- a/mysql-test/main/type_date.result +++ b/mysql-test/main/type_date.result @@ -1164,3 +1164,125 @@ set sql_mode=default; # # End of 10.4 tests # +# +# Start of 10.6 tests +# +# +# MDEV-32203 Raise notes when an index cannot be used on data type mismatch +# +SET note_verbosity=unusable_keys; +CREATE TABLE t1 (indexed_col DATE, KEY(indexed_col)); +FOR i IN 1..31 +DO +INSERT INTO t1 VALUES (MAKEDATE(2023, i)); +END FOR; +$$ +SELECT * FROM t1 WHERE indexed_col=20230101; +indexed_col +2023-01-01 +SELECT * FROM t1 WHERE indexed_col=20230101102030; +indexed_col +SELECT * FROM t1 WHERE indexed_col=20230101102030.1; +indexed_col +SELECT * FROM t1 WHERE indexed_col=20230101102030.1e0; +indexed_col +SELECT * FROM t1 WHERE indexed_col='10:20:30'; +indexed_col +Warnings: +Warning 1292 Truncated incorrect datetime value: '10:20:30' +SELECT * FROM t1 WHERE indexed_col='2001-01-01'; +indexed_col +SELECT * FROM t1 WHERE indexed_col='2001-01-01 10:20:30'; +indexed_col +SELECT * FROM t1 WHERE indexed_col=DATE'2001-01-01'; +indexed_col +SELECT * FROM t1 WHERE indexed_col=TIME'10:20:30'; +indexed_col +SELECT * FROM t1 WHERE indexed_col=TIMESTAMP'2001-01-01 10:20:30'; +indexed_col +SELECT * FROM t1 WHERE indexed_col=0x00; +indexed_col +Warnings: +Warning 1292 Truncated incorrect datetime value: '\x00' +SELECT * FROM t1 WHERE indexed_col=_utf8mb3'0' COLLATE utf8mb3_bin; +indexed_col +Warnings: +Warning 1292 Truncated incorrect datetime value: '0' +CREATE TABLE t2 (not_indexed_col INT); +INSERT INTO t2 VALUES (20230101),(20230102); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +2023-01-01 20230101 +2023-01-02 20230102 +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col INT UNSIGNED); +INSERT INTO t2 VALUES (20230101),(20230102); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +2023-01-01 20230101 +2023-01-02 20230102 +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col BIGINT); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col BIGINT UNSIGNED); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col DECIMAL(30,6)); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col FLOAT); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col DOUBLE); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col DATE); +INSERT INTO t2 VALUES ('2023-01-01'),('2023-01-02'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +2023-01-01 2023-01-01 +2023-01-02 2023-01-02 +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col DATETIME); +INSERT INTO t2 VALUES ('2023-01-01 00:00:00'),('2023-01-01 00:00:01'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +2023-01-01 2023-01-01 00:00:00 +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col TIMESTAMP); +INSERT INTO t2 VALUES ('2023-01-01 00:00:00'),('2023-01-01 00:00:01'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +2023-01-01 2023-01-01 00:00:00 +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col VARBINARY(32)); +INSERT INTO t2 VALUES (0x30),(0x31); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +Warnings: +Warning 1292 Incorrect datetime value: '0' +Warning 1292 Incorrect datetime value: '1' +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col VARCHAR(32)); +INSERT INTO t2 VALUES ('2001-01-01'),('2001-01-02'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col VARCHAR(32) CHARACTER SET utf8mb3); +INSERT INTO t2 VALUES ('2001-01-01'),('2001-01-02'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +DROP TABLE t1; +SET note_verbosity=DEFAULT; diff --git a/mysql-test/main/type_date.test b/mysql-test/main/type_date.test index 81cad6b5af5..d4981183c10 100644 --- a/mysql-test/main/type_date.test +++ b/mysql-test/main/type_date.test @@ -806,3 +806,26 @@ set sql_mode=default; --echo # --echo # End of 10.4 tests --echo # + + +--echo # +--echo # Start of 10.6 tests +--echo # + +--echo # +--echo # MDEV-32203 Raise notes when an index cannot be used on data type mismatch +--echo # + +SET note_verbosity=unusable_keys; +CREATE TABLE t1 (indexed_col DATE, KEY(indexed_col)); +DELIMITER $$; +FOR i IN 1..31 +DO + INSERT INTO t1 VALUES (MAKEDATE(2023, i)); +END FOR; +$$ +DELIMITER ;$$ +--source unusable_keys_literals.inc +--source unusable_keys_joins.inc +DROP TABLE t1; +SET note_verbosity=DEFAULT; diff --git a/mysql-test/main/type_datetime.result b/mysql-test/main/type_datetime.result index ff79c83eb47..282ff60f655 100644 --- a/mysql-test/main/type_datetime.result +++ b/mysql-test/main/type_datetime.result @@ -1587,3 +1587,125 @@ DROP TABLE t1; # # End of 10.4 tests # +# +# Start of 10.6 tests +# +# +# MDEV-32203 Raise notes when an index cannot be used on data type mismatch +# +SET note_verbosity=unusable_keys; +CREATE TABLE t1 (indexed_col DATETIME, KEY(indexed_col)); +FOR i IN 1..31 +DO +INSERT INTO t1 VALUES (MAKEDATE(2023, i)); +END FOR; +$$ +SELECT * FROM t1 WHERE indexed_col=20230101; +indexed_col +2023-01-01 00:00:00 +SELECT * FROM t1 WHERE indexed_col=20230101102030; +indexed_col +SELECT * FROM t1 WHERE indexed_col=20230101102030.1; +indexed_col +SELECT * FROM t1 WHERE indexed_col=20230101102030.1e0; +indexed_col +SELECT * FROM t1 WHERE indexed_col='10:20:30'; +indexed_col +Warnings: +Warning 1292 Truncated incorrect datetime value: '10:20:30' +SELECT * FROM t1 WHERE indexed_col='2001-01-01'; +indexed_col +SELECT * FROM t1 WHERE indexed_col='2001-01-01 10:20:30'; +indexed_col +SELECT * FROM t1 WHERE indexed_col=DATE'2001-01-01'; +indexed_col +SELECT * FROM t1 WHERE indexed_col=TIME'10:20:30'; +indexed_col +SELECT * FROM t1 WHERE indexed_col=TIMESTAMP'2001-01-01 10:20:30'; +indexed_col +SELECT * FROM t1 WHERE indexed_col=0x00; +indexed_col +Warnings: +Warning 1292 Truncated incorrect datetime value: '\x00' +SELECT * FROM t1 WHERE indexed_col=_utf8mb3'0' COLLATE utf8mb3_bin; +indexed_col +Warnings: +Warning 1292 Truncated incorrect datetime value: '0' +CREATE TABLE t2 (not_indexed_col INT); +INSERT INTO t2 VALUES (20230101),(20230102); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +2023-01-01 00:00:00 20230101 +2023-01-02 00:00:00 20230102 +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col INT UNSIGNED); +INSERT INTO t2 VALUES (20230101),(20230102); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +2023-01-01 00:00:00 20230101 +2023-01-02 00:00:00 20230102 +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col BIGINT); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col BIGINT UNSIGNED); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col DECIMAL(30,6)); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col FLOAT); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col DOUBLE); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col DATE); +INSERT INTO t2 VALUES ('2023-01-01'),('2023-01-02'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +2023-01-01 00:00:00 2023-01-01 +2023-01-02 00:00:00 2023-01-02 +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col DATETIME); +INSERT INTO t2 VALUES ('2023-01-01 00:00:00'),('2023-01-01 00:00:01'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +2023-01-01 00:00:00 2023-01-01 00:00:00 +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col TIMESTAMP); +INSERT INTO t2 VALUES ('2023-01-01 00:00:00'),('2023-01-01 00:00:01'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +2023-01-01 00:00:00 2023-01-01 00:00:00 +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col VARBINARY(32)); +INSERT INTO t2 VALUES (0x30),(0x31); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +Warnings: +Warning 1292 Incorrect datetime value: '0' +Warning 1292 Incorrect datetime value: '1' +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col VARCHAR(32)); +INSERT INTO t2 VALUES ('2001-01-01'),('2001-01-02'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col VARCHAR(32) CHARACTER SET utf8mb3); +INSERT INTO t2 VALUES ('2001-01-01'),('2001-01-02'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +DROP TABLE t1; +SET note_verbosity=DEFAULT; diff --git a/mysql-test/main/type_datetime.test b/mysql-test/main/type_datetime.test index 4a14bee4319..3c46d10718f 100644 --- a/mysql-test/main/type_datetime.test +++ b/mysql-test/main/type_datetime.test @@ -1055,3 +1055,26 @@ DROP TABLE t1; --echo # --echo # End of 10.4 tests --echo # + + +--echo # +--echo # Start of 10.6 tests +--echo # + +--echo # +--echo # MDEV-32203 Raise notes when an index cannot be used on data type mismatch +--echo # + +SET note_verbosity=unusable_keys; +CREATE TABLE t1 (indexed_col DATETIME, KEY(indexed_col)); +DELIMITER $$; +FOR i IN 1..31 +DO + INSERT INTO t1 VALUES (MAKEDATE(2023, i)); +END FOR; +$$ +DELIMITER ;$$ +--source unusable_keys_literals.inc +--source unusable_keys_joins.inc +DROP TABLE t1; +SET note_verbosity=DEFAULT; diff --git a/mysql-test/main/type_enum.result b/mysql-test/main/type_enum.result index a935e3d63cb..df9c07c6ebe 100644 --- a/mysql-test/main/type_enum.result +++ b/mysql-test/main/type_enum.result @@ -1903,6 +1903,8 @@ EXPLAIN SELECT t1.* FROM t1,t2 WHERE t1.c1=t2.c1; id select_type table type possible_keys key key_len ref rows Extra 1 SIMPLE t1 system PRIMARY NULL NULL NULL 1 1 SIMPLE t2 index PRIMARY PRIMARY 1 NULL 2 Using where; Using index +Warnings: +Note 1105 Cannot use key `PRIMARY` part[0] for lookup: `test`.`t2`.`c1` of type `enum` = "`t1`.`c1`" of type `date` SELECT t1.* FROM t1 LEFT JOIN t2 USING (c1); c1 2001-01-01 @@ -1912,6 +1914,8 @@ EXPLAIN SELECT t1.* FROM t1 LEFT JOIN t2 USING (c1); id select_type table type possible_keys key key_len ref rows Extra 1 SIMPLE t1 system NULL NULL NULL NULL 1 1 SIMPLE t2 index PRIMARY PRIMARY 1 NULL 2 Using where; Using index +Warnings: +Note 1105 Cannot use key `PRIMARY` part[0] for lookup: `test`.`t2`.`c1` of type `enum` = "`t1`.`c1`" of type `date` DROP TABLE t1, t2; # # MDEV-6978 Bad results with join comparing case insensitive VARCHAR/ENUM/SET expression to a _bin ENUM column @@ -1942,6 +1946,8 @@ EXPLAIN SELECT t1.* FROM t1 LEFT JOIN t2 ON t1.c1 COLLATE latin1_swedish_ci=t2.c id select_type table type possible_keys key key_len ref rows Extra 1 SIMPLE t1 system NULL NULL NULL NULL 1 1 SIMPLE t2 index PRIMARY PRIMARY 1 NULL 2 Using where; Using index +Warnings: +Note 1105 Cannot use key `PRIMARY` part[0] for lookup: `test`.`t2`.`c1` of collation `latin1_bin` = "`t1`.`c1` collate latin1_swedish_ci" of collation `latin1_swedish_ci` DROP TABLE IF EXISTS t1,t2; CREATE TABLE t1 (c1 SET('a') CHARACTER SET latin1 PRIMARY KEY); INSERT INTO t1 VALUES ('a'); @@ -1969,6 +1975,8 @@ EXPLAIN SELECT t1.* FROM t1 LEFT JOIN t2 ON t1.c1 COLLATE latin1_swedish_ci=t2.c id select_type table type possible_keys key key_len ref rows Extra 1 SIMPLE t1 system NULL NULL NULL NULL 1 1 SIMPLE t2 index PRIMARY PRIMARY 1 NULL 2 Using where; Using index +Warnings: +Note 1105 Cannot use key `PRIMARY` part[0] for lookup: `test`.`t2`.`c1` of collation `latin1_bin` = "`t1`.`c1` collate latin1_swedish_ci" of collation `latin1_swedish_ci` DROP TABLE IF EXISTS t1,t2; CREATE TABLE t1 (c1 VARCHAR(10) CHARACTER SET latin1 PRIMARY KEY); INSERT INTO t1 VALUES ('a'); @@ -1996,6 +2004,8 @@ EXPLAIN SELECT t1.* FROM t1 LEFT JOIN t2 ON t1.c1 COLLATE latin1_swedish_ci=t2.c id select_type table type possible_keys key key_len ref rows Extra 1 SIMPLE t1 system NULL NULL NULL NULL 1 1 SIMPLE t2 index PRIMARY PRIMARY 1 NULL 2 Using where; Using index +Warnings: +Note 1105 Cannot use key `PRIMARY` part[0] for lookup: `test`.`t2`.`c1` of collation `latin1_bin` = "`t1`.`c1` collate latin1_swedish_ci" of collation `latin1_swedish_ci` DROP TABLE IF EXISTS t1,t2; # # MDEV-6991 GROUP_MIN_MAX optimization is erroneously applied in some cases @@ -2354,6 +2364,208 @@ a FLOOR(a) CEILING(a) TRUNCATE(a,0) ROUND(a) DROP TABLE t2; DROP TABLE t1; # +# MDEV-32203 Raise notes when an index cannot be used on data type mismatch +# +SET note_verbosity=unusable_keys; +CREATE TABLE t1 ( +indexed_col ENUM('2001','2002','2003','2004','2005','2006','2007','2008','2009','2010'), +KEY(indexed_col) +); +FOR i IN 1..10 +DO +INSERT INTO t1 VALUES (i); +END FOR; +$$ +SELECT * FROM t1 WHERE indexed_col=20230101; +indexed_col +SELECT * FROM t1 WHERE indexed_col=20230101102030; +indexed_col +SELECT * FROM t1 WHERE indexed_col=20230101102030.1; +indexed_col +SELECT * FROM t1 WHERE indexed_col=20230101102030.1e0; +indexed_col +SELECT * FROM t1 WHERE indexed_col='10:20:30'; +indexed_col +SELECT * FROM t1 WHERE indexed_col='2001-01-01'; +indexed_col +SELECT * FROM t1 WHERE indexed_col='2001-01-01 10:20:30'; +indexed_col +SELECT * FROM t1 WHERE indexed_col=DATE'2001-01-01'; +indexed_col +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `enum` = "DATE'2001-01-01'" of type `date` +Warning 1292 Truncated incorrect datetime value: '2001' +Warning 1292 Truncated incorrect datetime value: '2002' +Warning 1292 Truncated incorrect datetime value: '2003' +Warning 1292 Truncated incorrect datetime value: '2004' +Warning 1292 Truncated incorrect datetime value: '2005' +Warning 1292 Truncated incorrect datetime value: '2006' +Warning 1292 Truncated incorrect datetime value: '2007' +Warning 1292 Truncated incorrect datetime value: '2008' +Warning 1292 Truncated incorrect datetime value: '2009' +Warning 1292 Truncated incorrect datetime value: '2010' +SELECT * FROM t1 WHERE indexed_col=TIME'10:20:30'; +indexed_col +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `enum` = "TIME'10:20:30'" of type `time` +SELECT * FROM t1 WHERE indexed_col=TIMESTAMP'2001-01-01 10:20:30'; +indexed_col +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `enum` = "TIMESTAMP'2001-01-01 10:20:30'" of type `datetime` +Warning 1292 Truncated incorrect datetime value: '2001' +Warning 1292 Truncated incorrect datetime value: '2002' +Warning 1292 Truncated incorrect datetime value: '2003' +Warning 1292 Truncated incorrect datetime value: '2004' +Warning 1292 Truncated incorrect datetime value: '2005' +Warning 1292 Truncated incorrect datetime value: '2006' +Warning 1292 Truncated incorrect datetime value: '2007' +Warning 1292 Truncated incorrect datetime value: '2008' +Warning 1292 Truncated incorrect datetime value: '2009' +Warning 1292 Truncated incorrect datetime value: '2010' +SELECT * FROM t1 WHERE indexed_col=0x00; +indexed_col +SELECT * FROM t1 WHERE indexed_col=_utf8mb3'0' COLLATE utf8mb3_bin; +indexed_col +Warnings: +Note 1105 Cannot use key parts with `test`.`t1`.`indexed_col` in the rewritten condition: `convert(``t1``.``indexed_col`` using utf8mb3) = _utf8mb3'0' collate utf8mb3_bin` +CREATE TABLE t2 (not_indexed_col INT); +INSERT INTO t2 VALUES (20230101),(20230102); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col INT UNSIGNED); +INSERT INTO t2 VALUES (20230101),(20230102); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col BIGINT); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col BIGINT UNSIGNED); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col DECIMAL(30,6)); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col FLOAT); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col DOUBLE); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col DATE); +INSERT INTO t2 VALUES ('2023-01-01'),('2023-01-02'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `enum` = "`t2`.`not_indexed_col`" of type `date` +Warning 1292 Truncated incorrect datetime value: '2001' +Warning 1292 Truncated incorrect datetime value: '2002' +Warning 1292 Truncated incorrect datetime value: '2003' +Warning 1292 Truncated incorrect datetime value: '2004' +Warning 1292 Truncated incorrect datetime value: '2005' +Warning 1292 Truncated incorrect datetime value: '2006' +Warning 1292 Truncated incorrect datetime value: '2007' +Warning 1292 Truncated incorrect datetime value: '2008' +Warning 1292 Truncated incorrect datetime value: '2009' +Warning 1292 Truncated incorrect datetime value: '2010' +Warning 1292 Truncated incorrect datetime value: '2001' +Warning 1292 Truncated incorrect datetime value: '2002' +Warning 1292 Truncated incorrect datetime value: '2003' +Warning 1292 Truncated incorrect datetime value: '2004' +Warning 1292 Truncated incorrect datetime value: '2005' +Warning 1292 Truncated incorrect datetime value: '2006' +Warning 1292 Truncated incorrect datetime value: '2007' +Warning 1292 Truncated incorrect datetime value: '2008' +Warning 1292 Truncated incorrect datetime value: '2009' +Warning 1292 Truncated incorrect datetime value: '2010' +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col DATETIME); +INSERT INTO t2 VALUES ('2023-01-01 00:00:00'),('2023-01-01 00:00:01'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `enum` = "`t2`.`not_indexed_col`" of type `datetime` +Warning 1292 Truncated incorrect datetime value: '2001' +Warning 1292 Truncated incorrect datetime value: '2002' +Warning 1292 Truncated incorrect datetime value: '2003' +Warning 1292 Truncated incorrect datetime value: '2004' +Warning 1292 Truncated incorrect datetime value: '2005' +Warning 1292 Truncated incorrect datetime value: '2006' +Warning 1292 Truncated incorrect datetime value: '2007' +Warning 1292 Truncated incorrect datetime value: '2008' +Warning 1292 Truncated incorrect datetime value: '2009' +Warning 1292 Truncated incorrect datetime value: '2010' +Warning 1292 Truncated incorrect datetime value: '2001' +Warning 1292 Truncated incorrect datetime value: '2002' +Warning 1292 Truncated incorrect datetime value: '2003' +Warning 1292 Truncated incorrect datetime value: '2004' +Warning 1292 Truncated incorrect datetime value: '2005' +Warning 1292 Truncated incorrect datetime value: '2006' +Warning 1292 Truncated incorrect datetime value: '2007' +Warning 1292 Truncated incorrect datetime value: '2008' +Warning 1292 Truncated incorrect datetime value: '2009' +Warning 1292 Truncated incorrect datetime value: '2010' +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col TIMESTAMP); +INSERT INTO t2 VALUES ('2023-01-01 00:00:00'),('2023-01-01 00:00:01'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `enum` = "`t2`.`not_indexed_col`" of type `timestamp` +Warning 1292 Truncated incorrect datetime value: '2001' +Warning 1292 Truncated incorrect datetime value: '2002' +Warning 1292 Truncated incorrect datetime value: '2003' +Warning 1292 Truncated incorrect datetime value: '2004' +Warning 1292 Truncated incorrect datetime value: '2005' +Warning 1292 Truncated incorrect datetime value: '2006' +Warning 1292 Truncated incorrect datetime value: '2007' +Warning 1292 Truncated incorrect datetime value: '2008' +Warning 1292 Truncated incorrect datetime value: '2009' +Warning 1292 Truncated incorrect datetime value: '2010' +Warning 1292 Truncated incorrect datetime value: '2001' +Warning 1292 Truncated incorrect datetime value: '2002' +Warning 1292 Truncated incorrect datetime value: '2003' +Warning 1292 Truncated incorrect datetime value: '2004' +Warning 1292 Truncated incorrect datetime value: '2005' +Warning 1292 Truncated incorrect datetime value: '2006' +Warning 1292 Truncated incorrect datetime value: '2007' +Warning 1292 Truncated incorrect datetime value: '2008' +Warning 1292 Truncated incorrect datetime value: '2009' +Warning 1292 Truncated incorrect datetime value: '2010' +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col VARBINARY(32)); +INSERT INTO t2 VALUES (0x30),(0x31); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of collation `latin1_swedish_ci` = "`t2`.`not_indexed_col`" of collation `binary` +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col VARCHAR(32)); +INSERT INTO t2 VALUES ('2001-01-01'),('2001-01-02'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col VARCHAR(32) CHARACTER SET utf8mb3); +INSERT INTO t2 VALUES ('2001-01-01'),('2001-01-02'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +Warnings: +Note 1105 Cannot use key parts with `test`.`t1`.`indexed_col` in the rewritten condition: `convert(``t1``.``indexed_col`` using utf8mb3) = ``t2``.``not_indexed_col``` +DROP TABLE t2; +DROP TABLE t1; +SET note_verbosity=DEFAULT; +# # MDEV-29062 Wrong result set metadata for a mix of INT+ENUM # CREATE TABLE t1 diff --git a/mysql-test/main/type_enum.test b/mysql-test/main/type_enum.test index 30a10407f89..8cc5d1d603b 100644 --- a/mysql-test/main/type_enum.test +++ b/mysql-test/main/type_enum.test @@ -556,6 +556,26 @@ SELECT * FROM t2; DROP TABLE t2; DROP TABLE t1; +--echo # +--echo # MDEV-32203 Raise notes when an index cannot be used on data type mismatch +--echo # + +SET note_verbosity=unusable_keys; +CREATE TABLE t1 ( + indexed_col ENUM('2001','2002','2003','2004','2005','2006','2007','2008','2009','2010'), + KEY(indexed_col) +); +DELIMITER $$; +FOR i IN 1..10 +DO + INSERT INTO t1 VALUES (i); +END FOR; +$$ +DELIMITER ;$$ +--source unusable_keys_literals.inc +--source unusable_keys_joins.inc +DROP TABLE t1; +SET note_verbosity=DEFAULT; --echo # --echo # MDEV-29062 Wrong result set metadata for a mix of INT+ENUM diff --git a/mysql-test/main/type_float.result b/mysql-test/main/type_float.result index ddb80bf24e8..9f01f22b3c7 100644 --- a/mysql-test/main/type_float.result +++ b/mysql-test/main/type_float.result @@ -538,6 +538,8 @@ EXPLAIN SELECT t1.* FROM t1 LEFT JOIN t2 ON t1.a=t2.a; id select_type table type possible_keys key key_len ref rows Extra 1 SIMPLE t1 system NULL NULL NULL NULL 1 1 SIMPLE t2 index PRIMARY PRIMARY 8 NULL 2 Using where; Using index +Warnings: +Note 1105 Cannot use key `PRIMARY` part[0] for lookup: `test`.`t2`.`a` of type `double` = "`t1`.`a`" of type `datetime` DROP TABLE t1,t2; # # MDEV-6971 Bad results with joins comparing TIME and DOUBLE/DECIMAL columns @@ -568,6 +570,8 @@ EXPLAIN SELECT t1.* FROM t1 LEFT JOIN t2 USING(a); id select_type table type possible_keys key key_len ref rows Extra 1 SIMPLE t1 system NULL NULL NULL NULL 1 1 SIMPLE t2 index PRIMARY PRIMARY 8 NULL 2 Using where; Using index +Warnings: +Note 1105 Cannot use key `PRIMARY` part[0] for lookup: `test`.`t2`.`a` of type `double` = "`t1`.`a`" of type `time` DROP TABLE t1,t2; # # End of 10.0 tests @@ -1170,6 +1174,262 @@ fdec 123.456.789,12345678900000000000000000000000000000 # End of 10.4 tests # # +# MDEV-32203 Raise notes when an index cannot be used on data type mismatch +# +SET note_verbosity=unusable_keys; +CREATE TABLE t1 (indexed_col FLOAT, KEY(indexed_col)); +FOR i IN 1..31 +DO +INSERT INTO t1 VALUES (MAKEDATE(2023, i)); +END FOR; +$$ +SELECT * FROM t1 WHERE indexed_col=20230101; +indexed_col +SELECT * FROM t1 WHERE indexed_col=20230101102030; +indexed_col +SELECT * FROM t1 WHERE indexed_col=20230101102030.1; +indexed_col +SELECT * FROM t1 WHERE indexed_col=20230101102030.1e0; +indexed_col +SELECT * FROM t1 WHERE indexed_col='10:20:30'; +indexed_col +SELECT * FROM t1 WHERE indexed_col='2001-01-01'; +indexed_col +SELECT * FROM t1 WHERE indexed_col='2001-01-01 10:20:30'; +indexed_col +SELECT * FROM t1 WHERE indexed_col=DATE'2001-01-01'; +indexed_col +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `float` = "DATE'2001-01-01'" of type `date` +Warning 1292 Incorrect datetime value: '20230132' for column `test`.`t1`.`indexed_col` at row 31 +SELECT * FROM t1 WHERE indexed_col=TIME'10:20:30'; +indexed_col +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `float` = "TIME'10:20:30'" of type `time` +Warning 1292 Incorrect time value: '20230132' for column `test`.`t1`.`indexed_col` at row 31 +SELECT * FROM t1 WHERE indexed_col=TIMESTAMP'2001-01-01 10:20:30'; +indexed_col +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `float` = "TIMESTAMP'2001-01-01 10:20:30'" of type `datetime` +Warning 1292 Incorrect datetime value: '20230132' for column `test`.`t1`.`indexed_col` at row 31 +SELECT * FROM t1 WHERE indexed_col=0x00; +indexed_col +SELECT * FROM t1 WHERE indexed_col=_utf8mb3'0' COLLATE utf8mb3_bin; +indexed_col +CREATE TABLE t2 (not_indexed_col INT); +INSERT INTO t2 VALUES (20230101),(20230102); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +20230100 20230102 +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col INT UNSIGNED); +INSERT INTO t2 VALUES (20230101),(20230102); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +20230100 20230102 +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col BIGINT); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col BIGINT UNSIGNED); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col DECIMAL(30,6)); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col FLOAT); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col DOUBLE); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col DATE); +INSERT INTO t2 VALUES ('2023-01-01'),('2023-01-02'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +20230100 2023-01-02 +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `float` = "`t2`.`not_indexed_col`" of type `date` +Warning 1292 Incorrect datetime value: '20230132' for column `test`.`t1`.`indexed_col` at row 31 +Warning 1292 Incorrect datetime value: '20230132' for column `test`.`t1`.`indexed_col` at row 31 +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col DATETIME); +INSERT INTO t2 VALUES ('2023-01-01 00:00:00'),('2023-01-01 00:00:01'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `float` = "`t2`.`not_indexed_col`" of type `datetime` +Warning 1292 Incorrect datetime value: '20230132' for column `test`.`t1`.`indexed_col` at row 31 +Warning 1292 Incorrect datetime value: '20230132' for column `test`.`t1`.`indexed_col` at row 31 +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col TIMESTAMP); +INSERT INTO t2 VALUES ('2023-01-01 00:00:00'),('2023-01-01 00:00:01'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `float` = "`t2`.`not_indexed_col`" of type `timestamp` +Warning 1292 Incorrect datetime value: '20230132' for column `test`.`t1`.`indexed_col` at row 31 +Warning 1292 Incorrect datetime value: '20230132' for column `test`.`t1`.`indexed_col` at row 31 +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col VARBINARY(32)); +INSERT INTO t2 VALUES (0x30),(0x31); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col VARCHAR(32)); +INSERT INTO t2 VALUES ('2001-01-01'),('2001-01-02'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +Warnings: +Warning 1292 Truncated incorrect DOUBLE value: '2001-01-01' +Warning 1292 Truncated incorrect DOUBLE value: '2001-01-02' +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col VARCHAR(32) CHARACTER SET utf8mb3); +INSERT INTO t2 VALUES ('2001-01-01'),('2001-01-02'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +Warnings: +Warning 1292 Truncated incorrect DOUBLE value: '2001-01-01' +Warning 1292 Truncated incorrect DOUBLE value: '2001-01-02' +DROP TABLE t2; +DROP TABLE t1; +SET note_verbosity=DEFAULT; +SET note_verbosity=unusable_keys; +CREATE TABLE t1 (indexed_col DOUBLE, KEY(indexed_col)); +FOR i IN 1..31 +DO +INSERT INTO t1 VALUES (MAKEDATE(2023, i)); +END FOR; +$$ +SELECT * FROM t1 WHERE indexed_col=20230101; +indexed_col +20230101 +SELECT * FROM t1 WHERE indexed_col=20230101102030; +indexed_col +SELECT * FROM t1 WHERE indexed_col=20230101102030.1; +indexed_col +SELECT * FROM t1 WHERE indexed_col=20230101102030.1e0; +indexed_col +SELECT * FROM t1 WHERE indexed_col='10:20:30'; +indexed_col +SELECT * FROM t1 WHERE indexed_col='2001-01-01'; +indexed_col +SELECT * FROM t1 WHERE indexed_col='2001-01-01 10:20:30'; +indexed_col +SELECT * FROM t1 WHERE indexed_col=DATE'2001-01-01'; +indexed_col +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `double` = "DATE'2001-01-01'" of type `date` +SELECT * FROM t1 WHERE indexed_col=TIME'10:20:30'; +indexed_col +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `double` = "TIME'10:20:30'" of type `time` +SELECT * FROM t1 WHERE indexed_col=TIMESTAMP'2001-01-01 10:20:30'; +indexed_col +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `double` = "TIMESTAMP'2001-01-01 10:20:30'" of type `datetime` +SELECT * FROM t1 WHERE indexed_col=0x00; +indexed_col +SELECT * FROM t1 WHERE indexed_col=_utf8mb3'0' COLLATE utf8mb3_bin; +indexed_col +CREATE TABLE t2 (not_indexed_col INT); +INSERT INTO t2 VALUES (20230101),(20230102); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +20230101 20230101 +20230102 20230102 +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col INT UNSIGNED); +INSERT INTO t2 VALUES (20230101),(20230102); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +20230101 20230101 +20230102 20230102 +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col BIGINT); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col BIGINT UNSIGNED); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col DECIMAL(30,6)); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col FLOAT); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col DOUBLE); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col DATE); +INSERT INTO t2 VALUES ('2023-01-01'),('2023-01-02'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +20230101 2023-01-01 +20230102 2023-01-02 +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `double` = "`t2`.`not_indexed_col`" of type `date` +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col DATETIME); +INSERT INTO t2 VALUES ('2023-01-01 00:00:00'),('2023-01-01 00:00:01'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +20230101 2023-01-01 00:00:00 +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `double` = "`t2`.`not_indexed_col`" of type `datetime` +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col TIMESTAMP); +INSERT INTO t2 VALUES ('2023-01-01 00:00:00'),('2023-01-01 00:00:01'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +20230101 2023-01-01 00:00:00 +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `double` = "`t2`.`not_indexed_col`" of type `timestamp` +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col VARBINARY(32)); +INSERT INTO t2 VALUES (0x30),(0x31); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col VARCHAR(32)); +INSERT INTO t2 VALUES ('2001-01-01'),('2001-01-02'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +Warnings: +Warning 1292 Truncated incorrect DOUBLE value: '2001-01-01' +Warning 1292 Truncated incorrect DOUBLE value: '2001-01-02' +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col VARCHAR(32) CHARACTER SET utf8mb3); +INSERT INTO t2 VALUES ('2001-01-01'),('2001-01-02'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +Warnings: +Warning 1292 Truncated incorrect DOUBLE value: '2001-01-01' +Warning 1292 Truncated incorrect DOUBLE value: '2001-01-02' +DROP TABLE t2; +DROP TABLE t1; +SET note_verbosity=DEFAULT; +# # Start of 10.9 tests # # diff --git a/mysql-test/main/type_float.test b/mysql-test/main/type_float.test index 6a1636cf9b9..12e3f070fde 100644 --- a/mysql-test/main/type_float.test +++ b/mysql-test/main/type_float.test @@ -720,6 +720,37 @@ DELIMITER ;$$ --echo # End of 10.4 tests --echo # +--echo # +--echo # MDEV-32203 Raise notes when an index cannot be used on data type mismatch +--echo # + +SET note_verbosity=unusable_keys; +CREATE TABLE t1 (indexed_col FLOAT, KEY(indexed_col)); +DELIMITER $$; +FOR i IN 1..31 +DO + INSERT INTO t1 VALUES (MAKEDATE(2023, i)); +END FOR; +$$ +DELIMITER ;$$ +--source unusable_keys_literals.inc +--source unusable_keys_joins.inc +DROP TABLE t1; +SET note_verbosity=DEFAULT; + +SET note_verbosity=unusable_keys; +CREATE TABLE t1 (indexed_col DOUBLE, KEY(indexed_col)); +DELIMITER $$; +FOR i IN 1..31 +DO + INSERT INTO t1 VALUES (MAKEDATE(2023, i)); +END FOR; +$$ +DELIMITER ;$$ +--source unusable_keys_literals.inc +--source unusable_keys_joins.inc +DROP TABLE t1; +SET note_verbosity=DEFAULT; --echo # --echo # Start of 10.9 tests diff --git a/mysql-test/main/type_int.result b/mysql-test/main/type_int.result index c25b213c7c4..9a54c9a5287 100644 --- a/mysql-test/main/type_int.result +++ b/mysql-test/main/type_int.result @@ -1688,3 +1688,256 @@ drop table t1; # # End of 10.5 tests # +# +# MDEV-32203 Raise notes when an index cannot be used on data type mismatch +# +SET note_verbosity=unusable_keys; +CREATE TABLE t1 (indexed_col INT, KEY(indexed_col)); +FOR i IN 1..31 +DO +INSERT INTO t1 VALUES (MAKEDATE(2023, i)); +END FOR; +$$ +SELECT * FROM t1 WHERE indexed_col=20230101; +indexed_col +20230101 +SELECT * FROM t1 WHERE indexed_col=20230101102030; +indexed_col +SELECT * FROM t1 WHERE indexed_col=20230101102030.1; +indexed_col +SELECT * FROM t1 WHERE indexed_col=20230101102030.1e0; +indexed_col +SELECT * FROM t1 WHERE indexed_col='10:20:30'; +indexed_col +SELECT * FROM t1 WHERE indexed_col='2001-01-01'; +indexed_col +SELECT * FROM t1 WHERE indexed_col='2001-01-01 10:20:30'; +indexed_col +SELECT * FROM t1 WHERE indexed_col=DATE'2001-01-01'; +indexed_col +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `int` = "DATE'2001-01-01'" of type `date` +SELECT * FROM t1 WHERE indexed_col=TIME'10:20:30'; +indexed_col +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `int` = "TIME'10:20:30'" of type `time` +SELECT * FROM t1 WHERE indexed_col=TIMESTAMP'2001-01-01 10:20:30'; +indexed_col +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `int` = "TIMESTAMP'2001-01-01 10:20:30'" of type `datetime` +SELECT * FROM t1 WHERE indexed_col=0x00; +indexed_col +SELECT * FROM t1 WHERE indexed_col=_utf8mb3'0' COLLATE utf8mb3_bin; +indexed_col +CREATE TABLE t2 (not_indexed_col INT); +INSERT INTO t2 VALUES (20230101),(20230102); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +20230101 20230101 +20230102 20230102 +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col INT UNSIGNED); +INSERT INTO t2 VALUES (20230101),(20230102); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +20230101 20230101 +20230102 20230102 +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col BIGINT); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col BIGINT UNSIGNED); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col DECIMAL(30,6)); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col FLOAT); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col DOUBLE); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col DATE); +INSERT INTO t2 VALUES ('2023-01-01'),('2023-01-02'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +20230101 2023-01-01 +20230102 2023-01-02 +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `int` = "`t2`.`not_indexed_col`" of type `date` +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col DATETIME); +INSERT INTO t2 VALUES ('2023-01-01 00:00:00'),('2023-01-01 00:00:01'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +20230101 2023-01-01 00:00:00 +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `int` = "`t2`.`not_indexed_col`" of type `datetime` +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col TIMESTAMP); +INSERT INTO t2 VALUES ('2023-01-01 00:00:00'),('2023-01-01 00:00:01'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +20230101 2023-01-01 00:00:00 +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `int` = "`t2`.`not_indexed_col`" of type `timestamp` +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col VARBINARY(32)); +INSERT INTO t2 VALUES (0x30),(0x31); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col VARCHAR(32)); +INSERT INTO t2 VALUES ('2001-01-01'),('2001-01-02'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +Warnings: +Warning 1292 Truncated incorrect INTEGER value: '2001-01-01' +Warning 1292 Truncated incorrect INTEGER value: '2001-01-02' +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col VARCHAR(32) CHARACTER SET utf8mb3); +INSERT INTO t2 VALUES ('2001-01-01'),('2001-01-02'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +Warnings: +Warning 1292 Truncated incorrect INTEGER value: '2001-01-01' +Warning 1292 Truncated incorrect INTEGER value: '2001-01-02' +DROP TABLE t2; +DROP TABLE t1; +SET note_verbosity=DEFAULT; +SET note_verbosity=unusable_keys; +CREATE TABLE t1 (indexed_col BIGINT, KEY(indexed_col)); +FOR i IN 1..31 +DO +INSERT INTO t1 VALUES (MAKEDATE(2023, i)); +END FOR; +$$ +SELECT * FROM t1 WHERE indexed_col=20230101; +indexed_col +20230101 +SELECT * FROM t1 WHERE indexed_col=20230101102030; +indexed_col +SELECT * FROM t1 WHERE indexed_col=20230101102030.1; +indexed_col +SELECT * FROM t1 WHERE indexed_col=20230101102030.1e0; +indexed_col +SELECT * FROM t1 WHERE indexed_col='10:20:30'; +indexed_col +Warnings: +Warning 1292 Truncated incorrect DECIMAL value: '10:20:30' +SELECT * FROM t1 WHERE indexed_col='2001-01-01'; +indexed_col +Warnings: +Warning 1292 Truncated incorrect DECIMAL value: '2001-01-01' +SELECT * FROM t1 WHERE indexed_col='2001-01-01 10:20:30'; +indexed_col +Warnings: +Warning 1292 Truncated incorrect DECIMAL value: '2001-01-01 10:20:30' +SELECT * FROM t1 WHERE indexed_col=DATE'2001-01-01'; +indexed_col +SELECT * FROM t1 WHERE indexed_col=TIME'10:20:30'; +indexed_col +SELECT * FROM t1 WHERE indexed_col=TIMESTAMP'2001-01-01 10:20:30'; +indexed_col +SELECT * FROM t1 WHERE indexed_col=0x00; +indexed_col +SELECT * FROM t1 WHERE indexed_col=_utf8mb3'0' COLLATE utf8mb3_bin; +indexed_col +CREATE TABLE t2 (not_indexed_col INT); +INSERT INTO t2 VALUES (20230101),(20230102); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +20230101 20230101 +20230102 20230102 +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col INT UNSIGNED); +INSERT INTO t2 VALUES (20230101),(20230102); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +20230101 20230101 +20230102 20230102 +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col BIGINT); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col BIGINT UNSIGNED); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col DECIMAL(30,6)); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col FLOAT); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col DOUBLE); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col DATE); +INSERT INTO t2 VALUES ('2023-01-01'),('2023-01-02'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +20230101 2023-01-01 +20230102 2023-01-02 +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `bigint` = "`t2`.`not_indexed_col`" of type `date` +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col DATETIME); +INSERT INTO t2 VALUES ('2023-01-01 00:00:00'),('2023-01-01 00:00:01'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +20230101 2023-01-01 00:00:00 +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `bigint` = "`t2`.`not_indexed_col`" of type `datetime` +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col TIMESTAMP); +INSERT INTO t2 VALUES ('2023-01-01 00:00:00'),('2023-01-01 00:00:01'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +20230101 2023-01-01 00:00:00 +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `bigint` = "`t2`.`not_indexed_col`" of type `timestamp` +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col VARBINARY(32)); +INSERT INTO t2 VALUES (0x30),(0x31); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col VARCHAR(32)); +INSERT INTO t2 VALUES ('2001-01-01'),('2001-01-02'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +Warnings: +Warning 1292 Truncated incorrect INTEGER value: '2001-01-01' +Warning 1292 Truncated incorrect INTEGER value: '2001-01-02' +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col VARCHAR(32) CHARACTER SET utf8mb3); +INSERT INTO t2 VALUES ('2001-01-01'),('2001-01-02'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +Warnings: +Warning 1292 Truncated incorrect INTEGER value: '2001-01-01' +Warning 1292 Truncated incorrect INTEGER value: '2001-01-02' +DROP TABLE t2; +DROP TABLE t1; +SET note_verbosity=DEFAULT; diff --git a/mysql-test/main/type_int.test b/mysql-test/main/type_int.test index c339bfa1834..c47ab501116 100644 --- a/mysql-test/main/type_int.test +++ b/mysql-test/main/type_int.test @@ -567,3 +567,36 @@ drop table t1; --echo # --echo # End of 10.5 tests --echo # + + +--echo # +--echo # MDEV-32203 Raise notes when an index cannot be used on data type mismatch +--echo # + +SET note_verbosity=unusable_keys; +CREATE TABLE t1 (indexed_col INT, KEY(indexed_col)); +DELIMITER $$; +FOR i IN 1..31 +DO + INSERT INTO t1 VALUES (MAKEDATE(2023, i)); +END FOR; +$$ +DELIMITER ;$$ +--source unusable_keys_literals.inc +--source unusable_keys_joins.inc +DROP TABLE t1; +SET note_verbosity=DEFAULT; + +SET note_verbosity=unusable_keys; +CREATE TABLE t1 (indexed_col BIGINT, KEY(indexed_col)); +DELIMITER $$; +FOR i IN 1..31 +DO + INSERT INTO t1 VALUES (MAKEDATE(2023, i)); +END FOR; +$$ +DELIMITER ;$$ +--source unusable_keys_literals.inc +--source unusable_keys_joins.inc +DROP TABLE t1; +SET note_verbosity=DEFAULT; diff --git a/mysql-test/main/type_newdecimal.result b/mysql-test/main/type_newdecimal.result index d42de5b7e0d..f63aafefb7c 100644 --- a/mysql-test/main/type_newdecimal.result +++ b/mysql-test/main/type_newdecimal.result @@ -2134,6 +2134,8 @@ EXPLAIN SELECT t1.* FROM t1 LEFT JOIN t2 ON t1.a=t2.a; id select_type table type possible_keys key key_len ref rows Extra 1 SIMPLE t1 system NULL NULL NULL NULL 1 1 SIMPLE t2 index PRIMARY PRIMARY 14 NULL 2 Using where; Using index +Warnings: +Note 1105 Cannot use key `PRIMARY` part[0] for lookup: `test`.`t2`.`a` of type `decimal` = "`t1`.`a`" of type `datetime` DROP TABLE t1,t2; # # MDEV-6971 Bad results with joins comparing TIME and DOUBLE/DECIMAL columns @@ -2164,6 +2166,8 @@ EXPLAIN SELECT t1.* FROM t1 LEFT JOIN t2 USING(a); id select_type table type possible_keys key key_len ref rows Extra 1 SIMPLE t1 system NULL NULL NULL NULL 1 1 SIMPLE t2 index PRIMARY PRIMARY 14 NULL 2 Using where; Using index +Warnings: +Note 1105 Cannot use key `PRIMARY` part[0] for lookup: `test`.`t2`.`a` of type `decimal` = "`t1`.`a`" of type `time` DROP TABLE t1,t2; # # End of 10.0 tests @@ -2802,3 +2806,131 @@ DROP TABLE t2,t1; # # End of 10.4 tests # +# +# MDEV-32203 Raise notes when an index cannot be used on data type mismatch +# +SET note_verbosity=unusable_keys; +CREATE TABLE t1 (indexed_col DECIMAL(30,6), KEY(indexed_col)); +FOR i IN 1..31 +DO +INSERT INTO t1 VALUES (MAKEDATE(2023, i)); +END FOR; +$$ +SELECT * FROM t1 WHERE indexed_col=20230101; +indexed_col +20230101.000000 +SELECT * FROM t1 WHERE indexed_col=20230101102030; +indexed_col +SELECT * FROM t1 WHERE indexed_col=20230101102030.1; +indexed_col +SELECT * FROM t1 WHERE indexed_col=20230101102030.1e0; +indexed_col +SELECT * FROM t1 WHERE indexed_col='10:20:30'; +indexed_col +SELECT * FROM t1 WHERE indexed_col='2001-01-01'; +indexed_col +SELECT * FROM t1 WHERE indexed_col='2001-01-01 10:20:30'; +indexed_col +SELECT * FROM t1 WHERE indexed_col=DATE'2001-01-01'; +indexed_col +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `decimal` = "DATE'2001-01-01'" of type `date` +SELECT * FROM t1 WHERE indexed_col=TIME'10:20:30'; +indexed_col +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `decimal` = "TIME'10:20:30'" of type `time` +SELECT * FROM t1 WHERE indexed_col=TIMESTAMP'2001-01-01 10:20:30'; +indexed_col +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `decimal` = "TIMESTAMP'2001-01-01 10:20:30'" of type `datetime` +SELECT * FROM t1 WHERE indexed_col=0x00; +indexed_col +SELECT * FROM t1 WHERE indexed_col=_utf8mb3'0' COLLATE utf8mb3_bin; +indexed_col +CREATE TABLE t2 (not_indexed_col INT); +INSERT INTO t2 VALUES (20230101),(20230102); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +20230101.000000 20230101 +20230102.000000 20230102 +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col INT UNSIGNED); +INSERT INTO t2 VALUES (20230101),(20230102); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +20230101.000000 20230101 +20230102.000000 20230102 +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col BIGINT); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col BIGINT UNSIGNED); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col DECIMAL(30,6)); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col FLOAT); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col DOUBLE); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col DATE); +INSERT INTO t2 VALUES ('2023-01-01'),('2023-01-02'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +20230101.000000 2023-01-01 +20230102.000000 2023-01-02 +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `decimal` = "`t2`.`not_indexed_col`" of type `date` +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col DATETIME); +INSERT INTO t2 VALUES ('2023-01-01 00:00:00'),('2023-01-01 00:00:01'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +20230101.000000 2023-01-01 00:00:00 +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `decimal` = "`t2`.`not_indexed_col`" of type `datetime` +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col TIMESTAMP); +INSERT INTO t2 VALUES ('2023-01-01 00:00:00'),('2023-01-01 00:00:01'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +20230101.000000 2023-01-01 00:00:00 +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `decimal` = "`t2`.`not_indexed_col`" of type `timestamp` +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col VARBINARY(32)); +INSERT INTO t2 VALUES (0x30),(0x31); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col VARCHAR(32)); +INSERT INTO t2 VALUES ('2001-01-01'),('2001-01-02'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +Warnings: +Warning 1292 Truncated incorrect DECIMAL value: '2001-01-01' +Warning 1292 Truncated incorrect DECIMAL value: '2001-01-02' +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col VARCHAR(32) CHARACTER SET utf8mb3); +INSERT INTO t2 VALUES ('2001-01-01'),('2001-01-02'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +Warnings: +Warning 1292 Truncated incorrect DECIMAL value: '2001-01-01' +Warning 1292 Truncated incorrect DECIMAL value: '2001-01-02' +DROP TABLE t2; +DROP TABLE t1; +SET note_verbosity=DEFAULT; diff --git a/mysql-test/main/type_newdecimal.test b/mysql-test/main/type_newdecimal.test index af5dc43fbd3..af82b7d601c 100644 --- a/mysql-test/main/type_newdecimal.test +++ b/mysql-test/main/type_newdecimal.test @@ -2011,3 +2011,21 @@ DROP TABLE t2,t1; --echo # --echo # End of 10.4 tests --echo # + +--echo # +--echo # MDEV-32203 Raise notes when an index cannot be used on data type mismatch +--echo # + +SET note_verbosity=unusable_keys; +CREATE TABLE t1 (indexed_col DECIMAL(30,6), KEY(indexed_col)); +DELIMITER $$; +FOR i IN 1..31 +DO + INSERT INTO t1 VALUES (MAKEDATE(2023, i)); +END FOR; +$$ +DELIMITER ;$$ +--source unusable_keys_literals.inc +--source unusable_keys_joins.inc +DROP TABLE t1; +SET note_verbosity=DEFAULT; diff --git a/mysql-test/main/type_set.result b/mysql-test/main/type_set.result index 5821bbae984..bd8a0e95eaa 100644 --- a/mysql-test/main/type_set.result +++ b/mysql-test/main/type_set.result @@ -133,6 +133,8 @@ EXPLAIN SELECT t1.* FROM t1,t2 WHERE t1.c1=t2.c1; id select_type table type possible_keys key key_len ref rows Extra 1 SIMPLE t1 system PRIMARY NULL NULL NULL 1 1 SIMPLE t2 index PRIMARY PRIMARY 1 NULL 2 Using where; Using index +Warnings: +Note 1105 Cannot use key `PRIMARY` part[0] for lookup: `test`.`t2`.`c1` of type `set` = "`t1`.`c1`" of type `date` SELECT t1.* FROM t1 LEFT JOIN t2 ON t1.c1=t2.c1; c1 2001-01-01 @@ -142,6 +144,8 @@ EXPLAIN SELECT t1.* FROM t1 LEFT JOIN t2 ON t1.c1=t2.c1; id select_type table type possible_keys key key_len ref rows Extra 1 SIMPLE t1 system NULL NULL NULL NULL 1 1 SIMPLE t2 index PRIMARY PRIMARY 1 NULL 2 Using where; Using index +Warnings: +Note 1105 Cannot use key `PRIMARY` part[0] for lookup: `test`.`t2`.`c1` of type `set` = "`t1`.`c1`" of type `date` DROP TABLE t1, t2; # # MDEV-6978 Bad results with join comparing case insensitive VARCHAR/ENUM/SET expression to a _bin ENUM column @@ -172,6 +176,8 @@ EXPLAIN SELECT t1.* FROM t1 LEFT JOIN t2 ON t1.c1 COLLATE latin1_swedish_ci=t2.c id select_type table type possible_keys key key_len ref rows Extra 1 SIMPLE t1 system NULL NULL NULL NULL 1 1 SIMPLE t2 index PRIMARY PRIMARY 1 NULL 2 Using where; Using index +Warnings: +Note 1105 Cannot use key `PRIMARY` part[0] for lookup: `test`.`t2`.`c1` of collation `latin1_bin` = "`t1`.`c1` collate latin1_swedish_ci" of collation `latin1_swedish_ci` DROP TABLE IF EXISTS t1,t2; CREATE TABLE t1 (c1 SET('a') CHARACTER SET latin1 PRIMARY KEY); INSERT INTO t1 VALUES ('a'); @@ -199,6 +205,8 @@ EXPLAIN SELECT t1.* FROM t1 LEFT JOIN t2 ON t1.c1 COLLATE latin1_swedish_ci=t2.c id select_type table type possible_keys key key_len ref rows Extra 1 SIMPLE t1 system NULL NULL NULL NULL 1 1 SIMPLE t2 index PRIMARY PRIMARY 1 NULL 2 Using where; Using index +Warnings: +Note 1105 Cannot use key `PRIMARY` part[0] for lookup: `test`.`t2`.`c1` of collation `latin1_bin` = "`t1`.`c1` collate latin1_swedish_ci" of collation `latin1_swedish_ci` DROP TABLE IF EXISTS t1,t2; CREATE TABLE t1 (c1 VARCHAR(10) CHARACTER SET latin1 PRIMARY KEY); INSERT INTO t1 VALUES ('a'); @@ -226,6 +234,8 @@ EXPLAIN SELECT t1.* FROM t1 LEFT JOIN t2 ON t1.c1 COLLATE latin1_swedish_ci=t2.c id select_type table type possible_keys key key_len ref rows Extra 1 SIMPLE t1 system NULL NULL NULL NULL 1 1 SIMPLE t2 index PRIMARY PRIMARY 1 NULL 2 Using where; Using index +Warnings: +Note 1105 Cannot use key `PRIMARY` part[0] for lookup: `test`.`t2`.`c1` of collation `latin1_bin` = "`t1`.`c1` collate latin1_swedish_ci" of collation `latin1_swedish_ci` DROP TABLE IF EXISTS t1,t2; # # MDEV-6993 Bad results with join comparing DECIMAL and ENUM/SET columns @@ -380,6 +390,208 @@ a FLOOR(a) CEILING(a) TRUNCATE(a,0) ROUND(a) DROP TABLE t2; DROP TABLE t1; # +# MDEV-32203 Raise notes when an index cannot be used on data type mismatch +# +SET note_verbosity=unusable_keys; +CREATE TABLE t1 ( +indexed_col SET('2001','2002','2003','2004','2005','2006','2007','2008','2009','2010'), +KEY(indexed_col) +); +FOR i IN 1..10 +DO +INSERT INTO t1 VALUES (CONCAT(2000+i)); +END FOR; +$$ +SELECT * FROM t1 WHERE indexed_col=20230101; +indexed_col +SELECT * FROM t1 WHERE indexed_col=20230101102030; +indexed_col +SELECT * FROM t1 WHERE indexed_col=20230101102030.1; +indexed_col +SELECT * FROM t1 WHERE indexed_col=20230101102030.1e0; +indexed_col +SELECT * FROM t1 WHERE indexed_col='10:20:30'; +indexed_col +SELECT * FROM t1 WHERE indexed_col='2001-01-01'; +indexed_col +SELECT * FROM t1 WHERE indexed_col='2001-01-01 10:20:30'; +indexed_col +SELECT * FROM t1 WHERE indexed_col=DATE'2001-01-01'; +indexed_col +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `set` = "DATE'2001-01-01'" of type `date` +Warning 1292 Truncated incorrect datetime value: '2001' +Warning 1292 Truncated incorrect datetime value: '2002' +Warning 1292 Truncated incorrect datetime value: '2003' +Warning 1292 Truncated incorrect datetime value: '2004' +Warning 1292 Truncated incorrect datetime value: '2005' +Warning 1292 Truncated incorrect datetime value: '2006' +Warning 1292 Truncated incorrect datetime value: '2007' +Warning 1292 Truncated incorrect datetime value: '2008' +Warning 1292 Truncated incorrect datetime value: '2009' +Warning 1292 Truncated incorrect datetime value: '2010' +SELECT * FROM t1 WHERE indexed_col=TIME'10:20:30'; +indexed_col +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `set` = "TIME'10:20:30'" of type `time` +SELECT * FROM t1 WHERE indexed_col=TIMESTAMP'2001-01-01 10:20:30'; +indexed_col +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `set` = "TIMESTAMP'2001-01-01 10:20:30'" of type `datetime` +Warning 1292 Truncated incorrect datetime value: '2001' +Warning 1292 Truncated incorrect datetime value: '2002' +Warning 1292 Truncated incorrect datetime value: '2003' +Warning 1292 Truncated incorrect datetime value: '2004' +Warning 1292 Truncated incorrect datetime value: '2005' +Warning 1292 Truncated incorrect datetime value: '2006' +Warning 1292 Truncated incorrect datetime value: '2007' +Warning 1292 Truncated incorrect datetime value: '2008' +Warning 1292 Truncated incorrect datetime value: '2009' +Warning 1292 Truncated incorrect datetime value: '2010' +SELECT * FROM t1 WHERE indexed_col=0x00; +indexed_col +SELECT * FROM t1 WHERE indexed_col=_utf8mb3'0' COLLATE utf8mb3_bin; +indexed_col +Warnings: +Note 1105 Cannot use key parts with `test`.`t1`.`indexed_col` in the rewritten condition: `convert(``t1``.``indexed_col`` using utf8mb3) = _utf8mb3'0' collate utf8mb3_bin` +CREATE TABLE t2 (not_indexed_col INT); +INSERT INTO t2 VALUES (20230101),(20230102); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col INT UNSIGNED); +INSERT INTO t2 VALUES (20230101),(20230102); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col BIGINT); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col BIGINT UNSIGNED); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col DECIMAL(30,6)); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col FLOAT); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col DOUBLE); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col DATE); +INSERT INTO t2 VALUES ('2023-01-01'),('2023-01-02'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `set` = "`t2`.`not_indexed_col`" of type `date` +Warning 1292 Truncated incorrect datetime value: '2001' +Warning 1292 Truncated incorrect datetime value: '2002' +Warning 1292 Truncated incorrect datetime value: '2003' +Warning 1292 Truncated incorrect datetime value: '2004' +Warning 1292 Truncated incorrect datetime value: '2005' +Warning 1292 Truncated incorrect datetime value: '2006' +Warning 1292 Truncated incorrect datetime value: '2007' +Warning 1292 Truncated incorrect datetime value: '2008' +Warning 1292 Truncated incorrect datetime value: '2009' +Warning 1292 Truncated incorrect datetime value: '2010' +Warning 1292 Truncated incorrect datetime value: '2001' +Warning 1292 Truncated incorrect datetime value: '2002' +Warning 1292 Truncated incorrect datetime value: '2003' +Warning 1292 Truncated incorrect datetime value: '2004' +Warning 1292 Truncated incorrect datetime value: '2005' +Warning 1292 Truncated incorrect datetime value: '2006' +Warning 1292 Truncated incorrect datetime value: '2007' +Warning 1292 Truncated incorrect datetime value: '2008' +Warning 1292 Truncated incorrect datetime value: '2009' +Warning 1292 Truncated incorrect datetime value: '2010' +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col DATETIME); +INSERT INTO t2 VALUES ('2023-01-01 00:00:00'),('2023-01-01 00:00:01'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `set` = "`t2`.`not_indexed_col`" of type `datetime` +Warning 1292 Truncated incorrect datetime value: '2001' +Warning 1292 Truncated incorrect datetime value: '2002' +Warning 1292 Truncated incorrect datetime value: '2003' +Warning 1292 Truncated incorrect datetime value: '2004' +Warning 1292 Truncated incorrect datetime value: '2005' +Warning 1292 Truncated incorrect datetime value: '2006' +Warning 1292 Truncated incorrect datetime value: '2007' +Warning 1292 Truncated incorrect datetime value: '2008' +Warning 1292 Truncated incorrect datetime value: '2009' +Warning 1292 Truncated incorrect datetime value: '2010' +Warning 1292 Truncated incorrect datetime value: '2001' +Warning 1292 Truncated incorrect datetime value: '2002' +Warning 1292 Truncated incorrect datetime value: '2003' +Warning 1292 Truncated incorrect datetime value: '2004' +Warning 1292 Truncated incorrect datetime value: '2005' +Warning 1292 Truncated incorrect datetime value: '2006' +Warning 1292 Truncated incorrect datetime value: '2007' +Warning 1292 Truncated incorrect datetime value: '2008' +Warning 1292 Truncated incorrect datetime value: '2009' +Warning 1292 Truncated incorrect datetime value: '2010' +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col TIMESTAMP); +INSERT INTO t2 VALUES ('2023-01-01 00:00:00'),('2023-01-01 00:00:01'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `set` = "`t2`.`not_indexed_col`" of type `timestamp` +Warning 1292 Truncated incorrect datetime value: '2001' +Warning 1292 Truncated incorrect datetime value: '2002' +Warning 1292 Truncated incorrect datetime value: '2003' +Warning 1292 Truncated incorrect datetime value: '2004' +Warning 1292 Truncated incorrect datetime value: '2005' +Warning 1292 Truncated incorrect datetime value: '2006' +Warning 1292 Truncated incorrect datetime value: '2007' +Warning 1292 Truncated incorrect datetime value: '2008' +Warning 1292 Truncated incorrect datetime value: '2009' +Warning 1292 Truncated incorrect datetime value: '2010' +Warning 1292 Truncated incorrect datetime value: '2001' +Warning 1292 Truncated incorrect datetime value: '2002' +Warning 1292 Truncated incorrect datetime value: '2003' +Warning 1292 Truncated incorrect datetime value: '2004' +Warning 1292 Truncated incorrect datetime value: '2005' +Warning 1292 Truncated incorrect datetime value: '2006' +Warning 1292 Truncated incorrect datetime value: '2007' +Warning 1292 Truncated incorrect datetime value: '2008' +Warning 1292 Truncated incorrect datetime value: '2009' +Warning 1292 Truncated incorrect datetime value: '2010' +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col VARBINARY(32)); +INSERT INTO t2 VALUES (0x30),(0x31); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of collation `latin1_swedish_ci` = "`t2`.`not_indexed_col`" of collation `binary` +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col VARCHAR(32)); +INSERT INTO t2 VALUES ('2001-01-01'),('2001-01-02'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col VARCHAR(32) CHARACTER SET utf8mb3); +INSERT INTO t2 VALUES ('2001-01-01'),('2001-01-02'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +Warnings: +Note 1105 Cannot use key parts with `test`.`t1`.`indexed_col` in the rewritten condition: `convert(``t1``.``indexed_col`` using utf8mb3) = ``t2``.``not_indexed_col``` +DROP TABLE t2; +DROP TABLE t1; +SET note_verbosity=DEFAULT; +# # MDEV-29062 Wrong result set metadata for a mix of INT+ENUM # CREATE TABLE t1 diff --git a/mysql-test/main/type_set.test b/mysql-test/main/type_set.test index 0ef2d158c4d..95732681be4 100644 --- a/mysql-test/main/type_set.test +++ b/mysql-test/main/type_set.test @@ -262,6 +262,26 @@ SELECT * FROM t2; DROP TABLE t2; DROP TABLE t1; +--echo # +--echo # MDEV-32203 Raise notes when an index cannot be used on data type mismatch +--echo # + +SET note_verbosity=unusable_keys; +CREATE TABLE t1 ( + indexed_col SET('2001','2002','2003','2004','2005','2006','2007','2008','2009','2010'), + KEY(indexed_col) +); +DELIMITER $$; +FOR i IN 1..10 +DO + INSERT INTO t1 VALUES (CONCAT(2000+i)); +END FOR; +$$ +DELIMITER ;$$ +--source unusable_keys_literals.inc +--source unusable_keys_joins.inc +DROP TABLE t1; +SET note_verbosity=DEFAULT; --echo # --echo # MDEV-29062 Wrong result set metadata for a mix of INT+ENUM diff --git a/mysql-test/main/type_time.result b/mysql-test/main/type_time.result index 14aac18a154..88a012b76d4 100644 --- a/mysql-test/main/type_time.result +++ b/mysql-test/main/type_time.result @@ -2496,3 +2496,115 @@ DROP TABLE t1; # # End of 10.4 tests # +# +# MDEV-32203 Raise notes when an index cannot be used on data type mismatch +# +SET note_verbosity=unusable_keys; +CREATE TABLE t1 (indexed_col TIME, KEY(indexed_col)); +FOR i IN 1..15 +DO +INSERT INTO t1 VALUES (MAKETIME(0,0,i)); +END FOR; +$$ +SELECT * FROM t1 WHERE indexed_col=20230101; +indexed_col +SELECT * FROM t1 WHERE indexed_col=20230101102030; +indexed_col +SELECT * FROM t1 WHERE indexed_col=20230101102030.1; +indexed_col +SELECT * FROM t1 WHERE indexed_col=20230101102030.1e0; +indexed_col +SELECT * FROM t1 WHERE indexed_col='10:20:30'; +indexed_col +SELECT * FROM t1 WHERE indexed_col='2001-01-01'; +indexed_col +Warnings: +Warning 1292 Truncated incorrect time value: '2001-01-01' +SELECT * FROM t1 WHERE indexed_col='2001-01-01 10:20:30'; +indexed_col +SELECT * FROM t1 WHERE indexed_col=DATE'2001-01-01'; +indexed_col +SELECT * FROM t1 WHERE indexed_col=TIME'10:20:30'; +indexed_col +SELECT * FROM t1 WHERE indexed_col=TIMESTAMP'2001-01-01 10:20:30'; +indexed_col +SELECT * FROM t1 WHERE indexed_col=0x00; +indexed_col +Warnings: +Warning 1292 Truncated incorrect time value: '\x00' +SELECT * FROM t1 WHERE indexed_col=_utf8mb3'0' COLLATE utf8mb3_bin; +indexed_col +CREATE TABLE t2 (not_indexed_col INT); +INSERT INTO t2 VALUES (20230101),(20230102); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col INT UNSIGNED); +INSERT INTO t2 VALUES (20230101),(20230102); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col BIGINT); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col BIGINT UNSIGNED); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col DECIMAL(30,6)); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col FLOAT); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col DOUBLE); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col DATE); +INSERT INTO t2 VALUES ('2023-01-01'),('2023-01-02'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col DATETIME); +INSERT INTO t2 VALUES ('2023-01-01 00:00:00'),('2023-01-01 00:00:01'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col TIMESTAMP); +INSERT INTO t2 VALUES ('2023-01-01 00:00:00'),('2023-01-01 00:00:01'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col VARBINARY(32)); +INSERT INTO t2 VALUES (0x30),(0x31); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +00:00:01 1 +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col VARCHAR(32)); +INSERT INTO t2 VALUES ('2001-01-01'),('2001-01-02'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +Warnings: +Warning 1292 Truncated incorrect time value: '2001-01-01' +Warning 1292 Truncated incorrect time value: '2001-01-02' +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col VARCHAR(32) CHARACTER SET utf8mb3); +INSERT INTO t2 VALUES ('2001-01-01'),('2001-01-02'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +Warnings: +Warning 1292 Truncated incorrect time value: '2001-01-01' +Warning 1292 Truncated incorrect time value: '2001-01-02' +DROP TABLE t2; +DROP TABLE t1; +SET note_verbosity=DEFAULT; diff --git a/mysql-test/main/type_time.test b/mysql-test/main/type_time.test index a75b278b1de..6d33c96a637 100644 --- a/mysql-test/main/type_time.test +++ b/mysql-test/main/type_time.test @@ -1623,3 +1623,21 @@ DROP TABLE t1; --echo # --echo # End of 10.4 tests --echo # + +--echo # +--echo # MDEV-32203 Raise notes when an index cannot be used on data type mismatch +--echo # + +SET note_verbosity=unusable_keys; +CREATE TABLE t1 (indexed_col TIME, KEY(indexed_col)); +DELIMITER $$; +FOR i IN 1..15 +DO + INSERT INTO t1 VALUES (MAKETIME(0,0,i)); +END FOR; +$$ +DELIMITER ;$$ +--source unusable_keys_literals.inc +--source unusable_keys_joins.inc +DROP TABLE t1; +SET note_verbosity=DEFAULT; diff --git a/mysql-test/main/type_timestamp.result b/mysql-test/main/type_timestamp.result index 8646b1f1d18..0789c84b2cf 100644 --- a/mysql-test/main/type_timestamp.result +++ b/mysql-test/main/type_timestamp.result @@ -1372,3 +1372,122 @@ drop table t1; # # End of 10.10 tests # +# +# MDEV-32203 Raise notes when an index cannot be used on data type mismatch +# +SET note_verbosity=unusable_keys; +CREATE TABLE t1 (indexed_col TIMESTAMP, KEY(indexed_col)); +FOR i IN 1..31 +DO +INSERT INTO t1 VALUES (MAKEDATE(2023, i)); +END FOR; +$$ +SELECT * FROM t1 WHERE indexed_col=20230101; +indexed_col +2023-01-01 00:00:00 +SELECT * FROM t1 WHERE indexed_col=20230101102030; +indexed_col +SELECT * FROM t1 WHERE indexed_col=20230101102030.1; +indexed_col +SELECT * FROM t1 WHERE indexed_col=20230101102030.1e0; +indexed_col +SELECT * FROM t1 WHERE indexed_col='10:20:30'; +indexed_col +Warnings: +Warning 1292 Incorrect datetime value: '10:20:30' +SELECT * FROM t1 WHERE indexed_col='2001-01-01'; +indexed_col +SELECT * FROM t1 WHERE indexed_col='2001-01-01 10:20:30'; +indexed_col +SELECT * FROM t1 WHERE indexed_col=DATE'2001-01-01'; +indexed_col +SELECT * FROM t1 WHERE indexed_col=TIME'10:20:30'; +indexed_col +SELECT * FROM t1 WHERE indexed_col=TIMESTAMP'2001-01-01 10:20:30'; +indexed_col +SELECT * FROM t1 WHERE indexed_col=0x00; +indexed_col +Warnings: +Warning 1292 Incorrect datetime value: '\x00' +SELECT * FROM t1 WHERE indexed_col=_utf8mb3'0' COLLATE utf8mb3_bin; +indexed_col +Warnings: +Warning 1292 Incorrect datetime value: '0' +CREATE TABLE t2 (not_indexed_col INT); +INSERT INTO t2 VALUES (20230101),(20230102); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +2023-01-01 00:00:00 20230101 +2023-01-02 00:00:00 20230102 +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col INT UNSIGNED); +INSERT INTO t2 VALUES (20230101),(20230102); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +2023-01-01 00:00:00 20230101 +2023-01-02 00:00:00 20230102 +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col BIGINT); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col BIGINT UNSIGNED); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col DECIMAL(30,6)); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col FLOAT); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col DOUBLE); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col DATE); +INSERT INTO t2 VALUES ('2023-01-01'),('2023-01-02'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +2023-01-01 00:00:00 2023-01-01 +2023-01-02 00:00:00 2023-01-02 +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col DATETIME); +INSERT INTO t2 VALUES ('2023-01-01 00:00:00'),('2023-01-01 00:00:01'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +2023-01-01 00:00:00 2023-01-01 00:00:00 +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col TIMESTAMP); +INSERT INTO t2 VALUES ('2023-01-01 00:00:00'),('2023-01-01 00:00:01'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +2023-01-01 00:00:00 2023-01-01 00:00:00 +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col VARBINARY(32)); +INSERT INTO t2 VALUES (0x30),(0x31); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +Warnings: +Warning 1292 Incorrect datetime value: '0' +Warning 1292 Incorrect datetime value: '1' +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col VARCHAR(32)); +INSERT INTO t2 VALUES ('2001-01-01'),('2001-01-02'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col VARCHAR(32) CHARACTER SET utf8mb3); +INSERT INTO t2 VALUES ('2001-01-01'),('2001-01-02'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +DROP TABLE t1; +SET note_verbosity=DEFAULT; diff --git a/mysql-test/main/type_timestamp.test b/mysql-test/main/type_timestamp.test index f869fa064d6..76589f1f6bc 100644 --- a/mysql-test/main/type_timestamp.test +++ b/mysql-test/main/type_timestamp.test @@ -923,3 +923,21 @@ drop table t1; --echo # --echo # End of 10.10 tests --echo # + +--echo # +--echo # MDEV-32203 Raise notes when an index cannot be used on data type mismatch +--echo # + +SET note_verbosity=unusable_keys; +CREATE TABLE t1 (indexed_col TIMESTAMP, KEY(indexed_col)); +DELIMITER $$; +FOR i IN 1..31 +DO + INSERT INTO t1 VALUES (MAKEDATE(2023, i)); +END FOR; +$$ +DELIMITER ;$$ +--source unusable_keys_literals.inc +--source unusable_keys_joins.inc +DROP TABLE t1; +SET note_verbosity=DEFAULT; diff --git a/mysql-test/main/type_uint.result b/mysql-test/main/type_uint.result index 7a90d6f0689..b4118edcd05 100644 --- a/mysql-test/main/type_uint.result +++ b/mysql-test/main/type_uint.result @@ -66,7 +66,262 @@ EXPLAIN SELECT t1.* FROM t1 LEFT JOIN t2 ON t1.a=t2.a; id select_type table type possible_keys key key_len ref rows Extra 1 SIMPLE t1 system NULL NULL NULL NULL 1 1 SIMPLE t2 index PRIMARY PRIMARY 4 NULL 2 Using where; Using index +Warnings: +Note 1105 Cannot use key `PRIMARY` part[0] for lookup: `test`.`t2`.`a` of type `int unsigned` = "`t1`.`a`" of type `date` DROP TABLE t1,t2; # # End of 10.0 tests # +# +# MDEV-32203 Raise notes when an index cannot be used on data type mismatch +# +SET note_verbosity=unusable_keys; +CREATE TABLE t1 (indexed_col INT UNSIGNED, KEY(indexed_col)); +FOR i IN 1..31 +DO +INSERT INTO t1 VALUES (MAKEDATE(2023, i)); +END FOR; +$$ +SELECT * FROM t1 WHERE indexed_col=20230101; +indexed_col +20230101 +SELECT * FROM t1 WHERE indexed_col=20230101102030; +indexed_col +SELECT * FROM t1 WHERE indexed_col=20230101102030.1; +indexed_col +SELECT * FROM t1 WHERE indexed_col=20230101102030.1e0; +indexed_col +SELECT * FROM t1 WHERE indexed_col='10:20:30'; +indexed_col +SELECT * FROM t1 WHERE indexed_col='2001-01-01'; +indexed_col +SELECT * FROM t1 WHERE indexed_col='2001-01-01 10:20:30'; +indexed_col +SELECT * FROM t1 WHERE indexed_col=DATE'2001-01-01'; +indexed_col +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `int unsigned` = "DATE'2001-01-01'" of type `date` +SELECT * FROM t1 WHERE indexed_col=TIME'10:20:30'; +indexed_col +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `int unsigned` = "TIME'10:20:30'" of type `time` +SELECT * FROM t1 WHERE indexed_col=TIMESTAMP'2001-01-01 10:20:30'; +indexed_col +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `int unsigned` = "TIMESTAMP'2001-01-01 10:20:30'" of type `datetime` +SELECT * FROM t1 WHERE indexed_col=0x00; +indexed_col +SELECT * FROM t1 WHERE indexed_col=_utf8mb3'0' COLLATE utf8mb3_bin; +indexed_col +CREATE TABLE t2 (not_indexed_col INT); +INSERT INTO t2 VALUES (20230101),(20230102); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +20230101 20230101 +20230102 20230102 +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col INT UNSIGNED); +INSERT INTO t2 VALUES (20230101),(20230102); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +20230101 20230101 +20230102 20230102 +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col BIGINT); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col BIGINT UNSIGNED); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col DECIMAL(30,6)); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col FLOAT); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col DOUBLE); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col DATE); +INSERT INTO t2 VALUES ('2023-01-01'),('2023-01-02'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +20230101 2023-01-01 +20230102 2023-01-02 +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `int unsigned` = "`t2`.`not_indexed_col`" of type `date` +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col DATETIME); +INSERT INTO t2 VALUES ('2023-01-01 00:00:00'),('2023-01-01 00:00:01'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +20230101 2023-01-01 00:00:00 +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `int unsigned` = "`t2`.`not_indexed_col`" of type `datetime` +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col TIMESTAMP); +INSERT INTO t2 VALUES ('2023-01-01 00:00:00'),('2023-01-01 00:00:01'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +20230101 2023-01-01 00:00:00 +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `int unsigned` = "`t2`.`not_indexed_col`" of type `timestamp` +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col VARBINARY(32)); +INSERT INTO t2 VALUES (0x30),(0x31); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col VARCHAR(32)); +INSERT INTO t2 VALUES ('2001-01-01'),('2001-01-02'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +Warnings: +Warning 1292 Truncated incorrect INTEGER value: '2001-01-01' +Warning 1292 Truncated incorrect INTEGER value: '2001-01-02' +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col VARCHAR(32) CHARACTER SET utf8mb3); +INSERT INTO t2 VALUES ('2001-01-01'),('2001-01-02'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +Warnings: +Warning 1292 Truncated incorrect INTEGER value: '2001-01-01' +Warning 1292 Truncated incorrect INTEGER value: '2001-01-02' +DROP TABLE t2; +DROP TABLE t1; +SET note_verbosity=DEFAULT; +SET note_verbosity=unusable_keys; +CREATE TABLE t1 (indexed_col BIGINT UNSIGNED, KEY(indexed_col)); +FOR i IN 1..31 +DO +INSERT INTO t1 VALUES (MAKEDATE(2023, i)); +END FOR; +$$ +SELECT * FROM t1 WHERE indexed_col=20230101; +indexed_col +20230101 +SELECT * FROM t1 WHERE indexed_col=20230101102030; +indexed_col +SELECT * FROM t1 WHERE indexed_col=20230101102030.1; +indexed_col +SELECT * FROM t1 WHERE indexed_col=20230101102030.1e0; +indexed_col +SELECT * FROM t1 WHERE indexed_col='10:20:30'; +indexed_col +Warnings: +Warning 1292 Truncated incorrect DECIMAL value: '10:20:30' +SELECT * FROM t1 WHERE indexed_col='2001-01-01'; +indexed_col +Warnings: +Warning 1292 Truncated incorrect DECIMAL value: '2001-01-01' +SELECT * FROM t1 WHERE indexed_col='2001-01-01 10:20:30'; +indexed_col +Warnings: +Warning 1292 Truncated incorrect DECIMAL value: '2001-01-01 10:20:30' +SELECT * FROM t1 WHERE indexed_col=DATE'2001-01-01'; +indexed_col +SELECT * FROM t1 WHERE indexed_col=TIME'10:20:30'; +indexed_col +SELECT * FROM t1 WHERE indexed_col=TIMESTAMP'2001-01-01 10:20:30'; +indexed_col +SELECT * FROM t1 WHERE indexed_col=0x00; +indexed_col +SELECT * FROM t1 WHERE indexed_col=_utf8mb3'0' COLLATE utf8mb3_bin; +indexed_col +CREATE TABLE t2 (not_indexed_col INT); +INSERT INTO t2 VALUES (20230101),(20230102); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +20230101 20230101 +20230102 20230102 +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col INT UNSIGNED); +INSERT INTO t2 VALUES (20230101),(20230102); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +20230101 20230101 +20230102 20230102 +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col BIGINT); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col BIGINT UNSIGNED); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col DECIMAL(30,6)); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col FLOAT); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col DOUBLE); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col DATE); +INSERT INTO t2 VALUES ('2023-01-01'),('2023-01-02'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +20230101 2023-01-01 +20230102 2023-01-02 +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `bigint unsigned` = "`t2`.`not_indexed_col`" of type `date` +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col DATETIME); +INSERT INTO t2 VALUES ('2023-01-01 00:00:00'),('2023-01-01 00:00:01'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +20230101 2023-01-01 00:00:00 +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `bigint unsigned` = "`t2`.`not_indexed_col`" of type `datetime` +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col TIMESTAMP); +INSERT INTO t2 VALUES ('2023-01-01 00:00:00'),('2023-01-01 00:00:01'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +20230101 2023-01-01 00:00:00 +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `bigint unsigned` = "`t2`.`not_indexed_col`" of type `timestamp` +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col VARBINARY(32)); +INSERT INTO t2 VALUES (0x30),(0x31); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col VARCHAR(32)); +INSERT INTO t2 VALUES ('2001-01-01'),('2001-01-02'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +Warnings: +Warning 1292 Truncated incorrect INTEGER value: '2001-01-01' +Warning 1292 Truncated incorrect INTEGER value: '2001-01-02' +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col VARCHAR(32) CHARACTER SET utf8mb3); +INSERT INTO t2 VALUES ('2001-01-01'),('2001-01-02'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +Warnings: +Warning 1292 Truncated incorrect INTEGER value: '2001-01-01' +Warning 1292 Truncated incorrect INTEGER value: '2001-01-02' +DROP TABLE t2; +DROP TABLE t1; +SET note_verbosity=DEFAULT; diff --git a/mysql-test/main/type_uint.test b/mysql-test/main/type_uint.test index ae48b30997a..72f32de848b 100644 --- a/mysql-test/main/type_uint.test +++ b/mysql-test/main/type_uint.test @@ -48,3 +48,36 @@ DROP TABLE t1,t2; --echo # --echo # End of 10.0 tests --echo # + + +--echo # +--echo # MDEV-32203 Raise notes when an index cannot be used on data type mismatch +--echo # + +SET note_verbosity=unusable_keys; +CREATE TABLE t1 (indexed_col INT UNSIGNED, KEY(indexed_col)); +DELIMITER $$; +FOR i IN 1..31 +DO + INSERT INTO t1 VALUES (MAKEDATE(2023, i)); +END FOR; +$$ +DELIMITER ;$$ +--source unusable_keys_literals.inc +--source unusable_keys_joins.inc +DROP TABLE t1; +SET note_verbosity=DEFAULT; + +SET note_verbosity=unusable_keys; +CREATE TABLE t1 (indexed_col BIGINT UNSIGNED, KEY(indexed_col)); +DELIMITER $$; +FOR i IN 1..31 +DO + INSERT INTO t1 VALUES (MAKEDATE(2023, i)); +END FOR; +$$ +DELIMITER ;$$ +--source unusable_keys_literals.inc +--source unusable_keys_joins.inc +DROP TABLE t1; +SET note_verbosity=DEFAULT; diff --git a/mysql-test/main/type_varchar.result b/mysql-test/main/type_varchar.result index ea31dddabda..bb752719caf 100644 --- a/mysql-test/main/type_varchar.result +++ b/mysql-test/main/type_varchar.result @@ -612,6 +612,8 @@ EXPLAIN SELECT t1.* FROM t1,t2 WHERE t1.c1=t2.c1; id select_type table type possible_keys key key_len ref rows Extra 1 SIMPLE t1 system PRIMARY NULL NULL NULL 1 1 SIMPLE t2 index PRIMARY PRIMARY 22 NULL 2 Using where; Using index +Warnings: +Note 1105 Cannot use key `PRIMARY` part[0] for lookup: `test`.`t2`.`c1` of type `varchar` = "`t1`.`c1`" of type `date` SELECT t1.* FROM t1 LEFT JOIN t2 ON t1.c1=t2.c1; c1 2001-01-01 @@ -621,6 +623,8 @@ EXPLAIN SELECT t1.* FROM t1 LEFT JOIN t2 ON t1.c1=t2.c1; id select_type table type possible_keys key key_len ref rows Extra 1 SIMPLE t1 system NULL NULL NULL NULL 1 1 SIMPLE t2 index PRIMARY PRIMARY 22 NULL 2 Using where; Using index +Warnings: +Note 1105 Cannot use key `PRIMARY` part[0] for lookup: `test`.`t2`.`c1` of type `varchar` = "`t1`.`c1`" of type `date` DROP TABLE IF EXISTS t1,t2; # # MDEV-6989 BINARY and COLLATE xxx_bin comparisions are not used for optimization in some cases @@ -767,3 +771,182 @@ DROP TABLE vchar; # # End of 10.5 tests # +# +# MDEV-32203 Raise notes when an index cannot be used on data type mismatch +# +SET note_verbosity=unusable_keys; +CREATE TABLE t1 (indexed_col VARCHAR(32), KEY(indexed_col)); +FOR i IN 1..31 +DO +INSERT INTO t1 VALUES (20230100+i); +END FOR; +$$ +SELECT * FROM t1 WHERE indexed_col=20230101; +indexed_col +20230101 +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `varchar` = "20230101" of type `int` +SELECT * FROM t1 WHERE indexed_col=20230101102030; +indexed_col +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `varchar` = "20230101102030" of type `bigint` +SELECT * FROM t1 WHERE indexed_col=20230101102030.1; +indexed_col +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `varchar` = "20230101102030.1" of type `decimal` +SELECT * FROM t1 WHERE indexed_col=20230101102030.1e0; +indexed_col +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `varchar` = "20230101102030.1e0" of type `double` +SELECT * FROM t1 WHERE indexed_col='10:20:30'; +indexed_col +SELECT * FROM t1 WHERE indexed_col='2001-01-01'; +indexed_col +SELECT * FROM t1 WHERE indexed_col='2001-01-01 10:20:30'; +indexed_col +SELECT * FROM t1 WHERE indexed_col=DATE'2001-01-01'; +indexed_col +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `varchar` = "DATE'2001-01-01'" of type `date` +SELECT * FROM t1 WHERE indexed_col=TIME'10:20:30'; +indexed_col +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `varchar` = "TIME'10:20:30'" of type `time` +Warning 1292 Truncated incorrect time value: '20230101' +Warning 1292 Truncated incorrect time value: '20230102' +Warning 1292 Truncated incorrect time value: '20230103' +Warning 1292 Truncated incorrect time value: '20230104' +Warning 1292 Truncated incorrect time value: '20230105' +Warning 1292 Truncated incorrect time value: '20230106' +Warning 1292 Truncated incorrect time value: '20230107' +Warning 1292 Truncated incorrect time value: '20230108' +Warning 1292 Truncated incorrect time value: '20230109' +Warning 1292 Truncated incorrect time value: '20230110' +Warning 1292 Truncated incorrect time value: '20230111' +Warning 1292 Truncated incorrect time value: '20230112' +Warning 1292 Truncated incorrect time value: '20230113' +Warning 1292 Truncated incorrect time value: '20230114' +Warning 1292 Truncated incorrect time value: '20230115' +Warning 1292 Truncated incorrect time value: '20230116' +Warning 1292 Truncated incorrect time value: '20230117' +Warning 1292 Truncated incorrect time value: '20230118' +Warning 1292 Truncated incorrect time value: '20230119' +Warning 1292 Truncated incorrect time value: '20230120' +Warning 1292 Truncated incorrect time value: '20230121' +Warning 1292 Truncated incorrect time value: '20230122' +Warning 1292 Truncated incorrect time value: '20230123' +Warning 1292 Truncated incorrect time value: '20230124' +Warning 1292 Truncated incorrect time value: '20230125' +Warning 1292 Truncated incorrect time value: '20230126' +Warning 1292 Truncated incorrect time value: '20230127' +Warning 1292 Truncated incorrect time value: '20230128' +Warning 1292 Truncated incorrect time value: '20230129' +Warning 1292 Truncated incorrect time value: '20230130' +Warning 1292 Truncated incorrect time value: '20230131' +SELECT * FROM t1 WHERE indexed_col=TIMESTAMP'2001-01-01 10:20:30'; +indexed_col +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `varchar` = "TIMESTAMP'2001-01-01 10:20:30'" of type `datetime` +SELECT * FROM t1 WHERE indexed_col=0x00; +indexed_col +SELECT * FROM t1 WHERE indexed_col=_utf8mb3'0' COLLATE utf8mb3_bin; +indexed_col +Warnings: +Note 1105 Cannot use key parts with `test`.`t1`.`indexed_col` in the rewritten condition: `convert(``t1``.``indexed_col`` using utf8mb3) = _utf8mb3'0' collate utf8mb3_bin` +CREATE TABLE t2 (not_indexed_col INT); +INSERT INTO t2 VALUES (20230101),(20230102); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +20230101 20230101 +20230102 20230102 +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `varchar` = "`t2`.`not_indexed_col`" of type `int` +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col INT UNSIGNED); +INSERT INTO t2 VALUES (20230101),(20230102); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +20230101 20230101 +20230102 20230102 +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `varchar` = "`t2`.`not_indexed_col`" of type `int unsigned` +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col BIGINT); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `varchar` = "`t2`.`not_indexed_col`" of type `bigint` +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col BIGINT UNSIGNED); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `varchar` = "`t2`.`not_indexed_col`" of type `bigint unsigned` +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col DECIMAL(30,6)); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `varchar` = "`t2`.`not_indexed_col`" of type `decimal` +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col FLOAT); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `varchar` = "`t2`.`not_indexed_col`" of type `float` +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col DOUBLE); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `varchar` = "`t2`.`not_indexed_col`" of type `double` +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col DATE); +INSERT INTO t2 VALUES ('2023-01-01'),('2023-01-02'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +20230101 2023-01-01 +20230102 2023-01-02 +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `varchar` = "`t2`.`not_indexed_col`" of type `date` +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col DATETIME); +INSERT INTO t2 VALUES ('2023-01-01 00:00:00'),('2023-01-01 00:00:01'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +20230101 2023-01-01 00:00:00 +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `varchar` = "`t2`.`not_indexed_col`" of type `datetime` +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col TIMESTAMP); +INSERT INTO t2 VALUES ('2023-01-01 00:00:00'),('2023-01-01 00:00:01'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +20230101 2023-01-01 00:00:00 +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `varchar` = "`t2`.`not_indexed_col`" of type `timestamp` +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col VARBINARY(32)); +INSERT INTO t2 VALUES (0x30),(0x31); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col VARCHAR(32)); +INSERT INTO t2 VALUES ('2001-01-01'),('2001-01-02'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col VARCHAR(32) CHARACTER SET utf8mb3); +INSERT INTO t2 VALUES ('2001-01-01'),('2001-01-02'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +Warnings: +Note 1105 Cannot use key parts with `test`.`t1`.`indexed_col` in the rewritten condition: `convert(``t1``.``indexed_col`` using utf8mb3) = ``t2``.``not_indexed_col``` +DROP TABLE t2; +DROP TABLE t1; +SET note_verbosity=DEFAULT; diff --git a/mysql-test/main/type_varchar.test b/mysql-test/main/type_varchar.test index f63523e226b..46b37554575 100644 --- a/mysql-test/main/type_varchar.test +++ b/mysql-test/main/type_varchar.test @@ -396,3 +396,22 @@ DROP TABLE vchar; --echo # --echo # End of 10.5 tests --echo # + + +--echo # +--echo # MDEV-32203 Raise notes when an index cannot be used on data type mismatch +--echo # + +SET note_verbosity=unusable_keys; +CREATE TABLE t1 (indexed_col VARCHAR(32), KEY(indexed_col)); +DELIMITER $$; +FOR i IN 1..31 +DO + INSERT INTO t1 VALUES (20230100+i); +END FOR; +$$ +DELIMITER ;$$ +--source unusable_keys_literals.inc +--source unusable_keys_joins.inc +DROP TABLE t1; +SET note_verbosity=DEFAULT; diff --git a/mysql-test/main/type_year.result b/mysql-test/main/type_year.result index cb5cce41232..278a8887d6d 100644 --- a/mysql-test/main/type_year.result +++ b/mysql-test/main/type_year.result @@ -703,3 +703,110 @@ DROP TABLE t1; # # End of 10.5 tests # +# +# MDEV-32203 Raise notes when an index cannot be used on data type mismatch +# +SET note_verbosity=unusable_keys; +CREATE TABLE t1 (indexed_col YEAR, KEY(indexed_col)); +FOR i IN 1..31 +DO +INSERT INTO t1 VALUES (2023 + i); +END FOR; +$$ +SELECT * FROM t1 WHERE indexed_col=20230101; +indexed_col +SELECT * FROM t1 WHERE indexed_col=20230101102030; +indexed_col +SELECT * FROM t1 WHERE indexed_col=20230101102030.1; +indexed_col +SELECT * FROM t1 WHERE indexed_col=20230101102030.1e0; +indexed_col +SELECT * FROM t1 WHERE indexed_col='10:20:30'; +indexed_col +SELECT * FROM t1 WHERE indexed_col='2001-01-01'; +indexed_col +SELECT * FROM t1 WHERE indexed_col='2001-01-01 10:20:30'; +indexed_col +SELECT * FROM t1 WHERE indexed_col=DATE'2001-01-01'; +indexed_col +SELECT * FROM t1 WHERE indexed_col=TIME'10:20:30'; +indexed_col +SELECT * FROM t1 WHERE indexed_col=TIMESTAMP'2001-01-01 10:20:30'; +indexed_col +SELECT * FROM t1 WHERE indexed_col=0x00; +indexed_col +SELECT * FROM t1 WHERE indexed_col=_utf8mb3'0' COLLATE utf8mb3_bin; +indexed_col +CREATE TABLE t2 (not_indexed_col INT); +INSERT INTO t2 VALUES (20230101),(20230102); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col INT UNSIGNED); +INSERT INTO t2 VALUES (20230101),(20230102); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col BIGINT); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col BIGINT UNSIGNED); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col DECIMAL(30,6)); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col FLOAT); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col DOUBLE); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col DATE); +INSERT INTO t2 VALUES ('2023-01-01'),('2023-01-02'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `year` = "`t2`.`not_indexed_col`" of type `date` +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col DATETIME); +INSERT INTO t2 VALUES ('2023-01-01 00:00:00'),('2023-01-01 00:00:01'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `year` = "`t2`.`not_indexed_col`" of type `datetime` +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col TIMESTAMP); +INSERT INTO t2 VALUES ('2023-01-01 00:00:00'),('2023-01-01 00:00:01'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +Warnings: +Note 1105 Cannot use key `indexed_col` part[0] for lookup: `test`.`t1`.`indexed_col` of type `year` = "`t2`.`not_indexed_col`" of type `timestamp` +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col VARBINARY(32)); +INSERT INTO t2 VALUES (0x30),(0x31); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col VARCHAR(32)); +INSERT INTO t2 VALUES ('2001-01-01'),('2001-01-02'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +CREATE TABLE t2 (not_indexed_col VARCHAR(32) CHARACTER SET utf8mb3); +INSERT INTO t2 VALUES ('2001-01-01'),('2001-01-02'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +indexed_col not_indexed_col +DROP TABLE t2; +DROP TABLE t1; +SET note_verbosity=DEFAULT; diff --git a/mysql-test/main/type_year.test b/mysql-test/main/type_year.test index 52783a21b74..2edb67a89eb 100644 --- a/mysql-test/main/type_year.test +++ b/mysql-test/main/type_year.test @@ -386,3 +386,22 @@ DROP TABLE t1; --echo # --echo # End of 10.5 tests --echo # + + +--echo # +--echo # MDEV-32203 Raise notes when an index cannot be used on data type mismatch +--echo # + +SET note_verbosity=unusable_keys; +CREATE TABLE t1 (indexed_col YEAR, KEY(indexed_col)); +DELIMITER $$; +FOR i IN 1..31 +DO + INSERT INTO t1 VALUES (2023 + i); +END FOR; +$$ +DELIMITER ;$$ +--source unusable_keys_literals.inc +--source unusable_keys_joins.inc +DROP TABLE t1; +SET note_verbosity=DEFAULT; diff --git a/mysql-test/main/unusable_keys_joins.inc b/mysql-test/main/unusable_keys_joins.inc new file mode 100644 index 00000000000..14d235fab30 --- /dev/null +++ b/mysql-test/main/unusable_keys_joins.inc @@ -0,0 +1,66 @@ +--enable_prepare_warnings +CREATE TABLE t2 (not_indexed_col INT); +INSERT INTO t2 VALUES (20230101),(20230102); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +DROP TABLE t2; + +CREATE TABLE t2 (not_indexed_col INT UNSIGNED); +INSERT INTO t2 VALUES (20230101),(20230102); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +DROP TABLE t2; + +CREATE TABLE t2 (not_indexed_col BIGINT); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +DROP TABLE t2; + +CREATE TABLE t2 (not_indexed_col BIGINT UNSIGNED); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +DROP TABLE t2; + +CREATE TABLE t2 (not_indexed_col DECIMAL(30,6)); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +DROP TABLE t2; + +CREATE TABLE t2 (not_indexed_col FLOAT); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +DROP TABLE t2; + +CREATE TABLE t2 (not_indexed_col DOUBLE); +INSERT INTO t2 VALUES (20230101102030),(20230101102031); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +DROP TABLE t2; + +CREATE TABLE t2 (not_indexed_col DATE); +INSERT INTO t2 VALUES ('2023-01-01'),('2023-01-02'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +DROP TABLE t2; + +CREATE TABLE t2 (not_indexed_col DATETIME); +INSERT INTO t2 VALUES ('2023-01-01 00:00:00'),('2023-01-01 00:00:01'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +DROP TABLE t2; + +CREATE TABLE t2 (not_indexed_col TIMESTAMP); +INSERT INTO t2 VALUES ('2023-01-01 00:00:00'),('2023-01-01 00:00:01'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +DROP TABLE t2; + +CREATE TABLE t2 (not_indexed_col VARBINARY(32)); +INSERT INTO t2 VALUES (0x30),(0x31); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +DROP TABLE t2; + +CREATE TABLE t2 (not_indexed_col VARCHAR(32)); +INSERT INTO t2 VALUES ('2001-01-01'),('2001-01-02'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +DROP TABLE t2; + +CREATE TABLE t2 (not_indexed_col VARCHAR(32) CHARACTER SET utf8mb3); +INSERT INTO t2 VALUES ('2001-01-01'),('2001-01-02'); +SELECT * FROM t1, t2 WHERE indexed_col=not_indexed_col; +DROP TABLE t2; +--disable_prepare_warnings diff --git a/mysql-test/main/unusable_keys_literals.inc b/mysql-test/main/unusable_keys_literals.inc new file mode 100644 index 00000000000..e19baa16f3c --- /dev/null +++ b/mysql-test/main/unusable_keys_literals.inc @@ -0,0 +1,14 @@ +--enable_prepare_warnings +SELECT * FROM t1 WHERE indexed_col=20230101; +SELECT * FROM t1 WHERE indexed_col=20230101102030; +SELECT * FROM t1 WHERE indexed_col=20230101102030.1; +SELECT * FROM t1 WHERE indexed_col=20230101102030.1e0; +SELECT * FROM t1 WHERE indexed_col='10:20:30'; +SELECT * FROM t1 WHERE indexed_col='2001-01-01'; +SELECT * FROM t1 WHERE indexed_col='2001-01-01 10:20:30'; +SELECT * FROM t1 WHERE indexed_col=DATE'2001-01-01'; +SELECT * FROM t1 WHERE indexed_col=TIME'10:20:30'; +SELECT * FROM t1 WHERE indexed_col=TIMESTAMP'2001-01-01 10:20:30'; +SELECT * FROM t1 WHERE indexed_col=0x00; +SELECT * FROM t1 WHERE indexed_col=_utf8mb3'0' COLLATE utf8mb3_bin; +--disable_prepare_warnings diff --git a/mysql-test/main/view.result b/mysql-test/main/view.result index 3b1ba75c9a6..01b7b99b3fc 100644 --- a/mysql-test/main/view.result +++ b/mysql-test/main/view.result @@ -7026,5 +7026,17 @@ ERROR HY000: View 'test.v' references invalid table(s) or column(s) or function( DROP VIEW v; DROP FUNCTION f; # +# MDEV-32164 Server crashes in JOIN::cleanup after erroneous query with +# view +# +CREATE TABLE t1 (a INT, b INT, KEY (a,b)) ENGINE=InnoDB; +CREATE VIEW v1 AS SELECT a FROM t1 WHERE a != '' GROUP BY a; +INSERT INTO t1 VALUES (1,NULL),(2,0),(3,NULL); +CREATE TABLE t2 (c INT) ENGINE=InnoDB; +CREATE TEMPORARY TABLE tmp SELECT v1.a FROM v1 JOIN t2 ON (v1.a = t2.c); +ERROR 22007: Truncated incorrect DECIMAL value: '' +DROP VIEW v1; +DROP TABLE t1, t2; +# # End of 10.6 tests # diff --git a/mysql-test/main/view.test b/mysql-test/main/view.test index ec948cafced..f44b536ae48 100644 --- a/mysql-test/main/view.test +++ b/mysql-test/main/view.test @@ -2,6 +2,7 @@ # Save the initial number of concurrent sessions. --source include/count_sessions.inc --source include/default_optimizer_switch.inc +--source include/have_innodb.inc SET optimizer_switch='outer_join_with_cache=off'; @@ -6783,6 +6784,21 @@ SELECT * FROM v; DROP VIEW v; DROP FUNCTION f; +--echo # +--echo # MDEV-32164 Server crashes in JOIN::cleanup after erroneous query with +--echo # view +--echo # + +CREATE TABLE t1 (a INT, b INT, KEY (a,b)) ENGINE=InnoDB; +CREATE VIEW v1 AS SELECT a FROM t1 WHERE a != '' GROUP BY a; +INSERT INTO t1 VALUES (1,NULL),(2,0),(3,NULL); +CREATE TABLE t2 (c INT) ENGINE=InnoDB; +--error ER_TRUNCATED_WRONG_VALUE +CREATE TEMPORARY TABLE tmp SELECT v1.a FROM v1 JOIN t2 ON (v1.a = t2.c); +# Cleanup +DROP VIEW v1; +DROP TABLE t1, t2; + --echo # --echo # End of 10.6 tests --echo # diff --git a/mysql-test/mariadb-test-run.pl b/mysql-test/mariadb-test-run.pl index c08b15be8ef..17c9496a158 100755 --- a/mysql-test/mariadb-test-run.pl +++ b/mysql-test/mariadb-test-run.pl @@ -351,7 +351,7 @@ $| = 1; # Automatically flush STDOUT main(); sub main { - $ENV{MTR_PERL}=$^X; + $ENV{MTR_PERL}= mixed_path($^X); # Default, verbosity on report_option('verbose', 0); @@ -499,7 +499,7 @@ sub main { mark_time_used('init'); my ($prefix, $fail, $completed, $extra_warnings)= - run_test_server($server, $tests, \%children); + Manager::run($server, $tests, \%children); exit(0) if $opt_start_exit; @@ -585,23 +585,205 @@ sub main { } -sub run_test_server ($$$) { +package Manager; +use POSIX ":sys_wait_h"; +use File::Basename; +use File::Find; +use IO::Socket::INET; +use IO::Select; +use mtr_report; +use My::Platform; + +my $num_saved_datadir; # Number of datadirs saved in vardir/log/ so far. +my $num_failed_test; # Number of tests failed so far +my $test_failure; # Set true if test suite failed +my $extra_warnings; # Warnings found during server shutdowns + +my $completed; +my %running; +my $result; +my $exe_mysqld; # Used as hint to CoreDump +my %names; + +sub parse_protocol($$) { + my $sock= shift; + my $line= shift; + + if ($line eq 'TESTRESULT'){ + mtr_verbose2("Got TESTRESULT from ". $names{$sock}); + $result= My::Test::read_test($sock); + + # Report test status + mtr_report_test($result); + + if ( $result->is_failed() ) { + + # Save the workers "savedir" in var/log + my $worker_savedir= $result->{savedir}; + my $worker_savename= basename($worker_savedir); + my $savedir= "$opt_vardir/log/$worker_savename"; + + # Move any core files from e.g. mysqltest + foreach my $coref (glob("core*"), glob("*.dmp")) + { + mtr_report(" - found '$coref', moving it to '$worker_savedir'"); + ::move($coref, $worker_savedir); + } + + find( + { + no_chdir => 1, + wanted => sub + { + My::CoreDump::core_wanted(\$num_saved_cores, + $opt_max_save_core, + @opt_cases == 0, + $exe_mysqld, $opt_parallel); + } + }, + $worker_savedir); + + if ($num_saved_datadir >= $opt_max_save_datadir) + { + mtr_report(" - skipping '$worker_savedir/'"); + main::rmtree($worker_savedir); + } + else + { + mtr_report(" - saving '$worker_savedir/' to '$savedir/'"); + rename($worker_savedir, $savedir); + $num_saved_datadir++; + } + main::resfile_print_test(); + $num_failed_test++ unless ($result->{retries} || + $result->{exp_fail}); + + $test_failure= 1; + if ( !$opt_force ) { + # Test has failed, force is off + push(@$completed, $result); + if ($result->{'dont_kill_server'}) + { + mtr_verbose2("${line}: saying BYE to ". $names{$sock}); + print $sock "BYE\n"; + return 2; + } + return ["Failure", 1, $completed, $extra_warnings]; + } + elsif ($opt_max_test_fail > 0 and + $num_failed_test >= $opt_max_test_fail) { + push(@$completed, $result); + mtr_report("Too many tests($num_failed_test) failed!", + "Terminating..."); + return ["Too many failed", 1, $completed, $extra_warnings]; + } + } + + main::resfile_print_test(); + # Retry test run after test failure + my $retries= $result->{retries} || 2; + my $test_has_failed= $result->{failures} || 0; + if ($test_has_failed and $retries <= $opt_retry){ + # Test should be run one more time unless it has failed + # too many times already + my $tname= $result->{name}; + my $failures= $result->{failures}; + if ($opt_retry > 1 and $failures >= $opt_retry_failure){ + mtr_report("\nTest $tname has failed $failures times,", + "no more retries!\n"); + } + else { + mtr_report("\nRetrying test $tname, ". + "attempt($retries/$opt_retry)...\n"); + #saving the log file as filename.failed in case of retry + if ( $result->is_failed() ) { + my $worker_logdir= $result->{savedir}; + my $log_file_name=dirname($worker_logdir)."/".$result->{shortname}.".log"; + + if (-e $log_file_name) { + $result->{'logfile-failed'} = ::mtr_lastlinesfromfile($log_file_name, 20); + } else { + $result->{'logfile-failed'} = ""; + } + + rename $log_file_name, $log_file_name.".failed"; + } + { + local @$result{'retries', 'result'}; + delete $result->{result}; + $result->{retries}= $retries+1; + $result->write_test($sock, 'TESTCASE'); + } + push(@$completed, $result); + return 2; + } + } + + # Repeat test $opt_repeat number of times + my $repeat= $result->{repeat} || 1; + if ($repeat < $opt_repeat) + { + $result->{retries}= 0; + $result->{rep_failures}++ if $result->{failures}; + $result->{failures}= 0; + delete($result->{result}); + $result->{repeat}= $repeat+1; + $result->write_test($sock, 'TESTCASE'); + return 2; + } + + # Remove from list of running + mtr_error("'", $result->{name},"' is not known to be running") + unless delete $running{$result->key()}; + + # Save result in completed list + push(@$completed, $result); + + } # if ($line eq 'TESTRESULT') + elsif ($line=~ /^START (.*)$/){ + # Send first test + $names{$sock}= $1; + } + elsif ($line eq 'WARNINGS'){ + my $fake_test= My::Test::read_test($sock); + my $test_list= join (" ", @{$fake_test->{testnames}}); + push @$extra_warnings, $test_list; + my $report= $fake_test->{'warnings'}; + mtr_report("***Warnings generated in error logs during shutdown ". + "after running tests: $test_list\n\n$report"); + $test_failure= 1; + if ( !$opt_force ) { + # Test failure due to warnings, force is off + mtr_verbose2("Socket loop exiting 3"); + return ["Warnings in log", 1, $completed, $extra_warnings]; + } + return 1; + } + elsif ($line =~ /^SPENT/) { + main::add_total_times($line); + } + elsif ($line eq 'VALGREP' && $opt_valgrind) { + $valgrind_reports= 1; + } + else { + mtr_error("Unknown response: '$line' from client"); + } + return 0; +} + +sub run ($$$) { my ($server, $tests, $children) = @_; - - my $num_saved_datadir= 0; # Number of datadirs saved in vardir/log/ so far. - my $num_failed_test= 0; # Number of tests failed so far - my $test_failure= 0; # Set true if test suite failed - my $extra_warnings= []; # Warnings found during server shutdowns - - my $completed= []; - my %running; - my $result; - my $exe_mysqld= find_mysqld($bindir) || ""; # Used as hint to CoreDump - - my $suite_timeout= start_timer(suite_timeout()); + my $suite_timeout= main::start_timer(main::suite_timeout()); + $exe_mysqld= main::find_mysqld($bindir) || ""; # Used as hint to CoreDump + $num_saved_datadir= 0; # Number of datadirs saved in vardir/log/ so far. + $num_failed_test= 0; # Number of tests failed so far + $test_failure= 0; # Set true if test suite failed + $extra_warnings= []; # Warnings found during server shutdowns + $completed= []; my $s= IO::Select->new(); my $childs= 0; + $s->add($server); while (1) { if ($opt_stop_file) @@ -609,190 +791,60 @@ sub run_test_server ($$$) { if (mtr_wait_lock_file($opt_stop_file, $opt_stop_keep_alive)) { # We were waiting so restart timer process - my $suite_timeout= start_timer(suite_timeout()); + my $suite_timeout= main::start_timer(main::suite_timeout()); } } - mark_time_used('admin'); + main::mark_time_used('admin'); my @ready = $s->can_read(1); # Wake up once every second - mtr_debug("Got ". (0 + @ready). " connection(s)"); - mark_time_idle(); - foreach my $sock (@ready) { + if (@ready > 0) { + mtr_verbose2("Got ". (0 + @ready). " connection(s)"); + } + main::mark_time_idle(); + my $i= 0; + sock_loop: foreach my $sock (@ready) { + ++$i; if ($sock == $server) { # New client connected ++$childs; my $child= $sock->accept(); - mtr_verbose2("Client connected (got ${childs} childs)"); + mtr_verbose2("Connection ${i}: Worker connected (got ${childs} childs)"); $s->add($child); print $child "HELLO\n"; } else { - my $line= <$sock>; - if (!defined $line) { - # Client disconnected - --$childs; - mtr_verbose2("Child closed socket (left ${childs} childs)"); - $s->remove($sock); - $sock->close; - next; - } - chomp($line); + my $j= 0; + $sock->blocking(0); + while (my $line= <$sock>) { + ++$j; + chomp($line); + mtr_verbose2("Connection ${i}.${j}". (exists $names{$sock} ? " from $names{$sock}" : "") .": $line"); - if ($line eq 'TESTRESULT'){ - $result= My::Test::read_test($sock); - - # Report test status - mtr_report_test($result); - - if ( $result->is_failed() ) { - - # Save the workers "savedir" in var/log - my $worker_savedir= $result->{savedir}; - my $worker_savename= basename($worker_savedir); - my $savedir= "$opt_vardir/log/$worker_savename"; - - # Move any core files from e.g. mysqltest - foreach my $coref (glob("core*"), glob("*.dmp")) - { - mtr_report(" - found '$coref', moving it to '$worker_savedir'"); - move($coref, $worker_savedir); - } - - find( - { - no_chdir => 1, - wanted => sub - { - My::CoreDump::core_wanted(\$num_saved_cores, - $opt_max_save_core, - @opt_cases == 0, - $exe_mysqld, $opt_parallel); - } - }, - $worker_savedir); - - if ($num_saved_datadir >= $opt_max_save_datadir) - { - mtr_report(" - skipping '$worker_savedir/'"); - rmtree($worker_savedir); - } - else - { - mtr_report(" - saving '$worker_savedir/' to '$savedir/'"); - rename($worker_savedir, $savedir); - $num_saved_datadir++; - } - resfile_print_test(); - $num_failed_test++ unless ($result->{retries} || - $result->{exp_fail}); - - $test_failure= 1; - if ( !$opt_force ) { - # Test has failed, force is off - push(@$completed, $result); - if ($result->{'dont_kill_server'}) - { - print $sock "BYE\n"; - next; - } - return ("Failure", 1, $completed, $extra_warnings); - } - elsif ($opt_max_test_fail > 0 and - $num_failed_test >= $opt_max_test_fail) { - push(@$completed, $result); - mtr_report("Too many tests($num_failed_test) failed!", - "Terminating..."); - return ("Too many failed", 1, $completed, $extra_warnings); - } - } - - resfile_print_test(); - # Retry test run after test failure - my $retries= $result->{retries} || 2; - my $test_has_failed= $result->{failures} || 0; - if ($test_has_failed and $retries <= $opt_retry){ - # Test should be run one more time unless it has failed - # too many times already - my $tname= $result->{name}; - my $failures= $result->{failures}; - if ($opt_retry > 1 and $failures >= $opt_retry_failure){ - mtr_report("\nTest $tname has failed $failures times,", - "no more retries!\n"); - } - else { - mtr_report("\nRetrying test $tname, ". - "attempt($retries/$opt_retry)...\n"); - #saving the log file as filename.failed in case of retry - if ( $result->is_failed() ) { - my $worker_logdir= $result->{savedir}; - my $log_file_name=dirname($worker_logdir)."/".$result->{shortname}.".log"; - - if (-e $log_file_name) { - $result->{'logfile-failed'} = mtr_lastlinesfromfile($log_file_name, 20); - } else { - $result->{'logfile-failed'} = ""; - } - - rename $log_file_name, $log_file_name.".failed"; - } - { - local @$result{'retries', 'result'}; - delete $result->{result}; - $result->{retries}= $retries+1; - $result->write_test($sock, 'TESTCASE'); - } - push(@$completed, $result); - next; - } - } - - # Repeat test $opt_repeat number of times - my $repeat= $result->{repeat} || 1; - if ($repeat < $opt_repeat) - { - $result->{retries}= 0; - $result->{rep_failures}++ if $result->{failures}; - $result->{failures}= 0; - delete($result->{result}); - $result->{repeat}= $repeat+1; - $result->write_test($sock, 'TESTCASE'); - next; - } - - # Remove from list of running - mtr_error("'", $result->{name},"' is not known to be running") - unless delete $running{$result->key()}; - - # Save result in completed list - push(@$completed, $result); - - } - elsif ($line eq 'START'){ - ; # Send first test - } - elsif ($line eq 'WARNINGS'){ - my $fake_test= My::Test::read_test($sock); - my $test_list= join (" ", @{$fake_test->{testnames}}); - push @$extra_warnings, $test_list; - my $report= $fake_test->{'warnings'}; - mtr_report("***Warnings generated in error logs during shutdown ". - "after running tests: $test_list\n\n$report"); - $test_failure= 1; - if ( !$opt_force ) { - # Test failure due to warnings, force is off - return ("Warnings in log", 1, $completed, $extra_warnings); + $sock->blocking(1); + my $res= parse_protocol($sock, $line); + $sock->blocking(0); + if (ref $res eq 'ARRAY') { + return @$res; + } elsif ($res == 1) { + next; + } elsif ($res == 2) { + next sock_loop; } + if (IS_WINDOWS and !IS_CYGWIN) { + # Strawberry and ActiveState don't support blocking(0), the next iteration will be blocked! + # If there is next response now in the buffer and it is TESTRESULT we are affected by MDEV-30836 and the manager will hang. + last; + } + } + $sock->blocking(1); + if ($j == 0) { + # Client disconnected + --$childs; + mtr_verbose2((exists $names{$sock} ? $names{$sock} : "Worker"). " closed socket (left ${childs} childs)"); + $s->remove($sock); + $sock->close; next; } - elsif ($line =~ /^SPENT/) { - add_total_times($line); - } - elsif ($line eq 'VALGREP' && $opt_valgrind) { - $valgrind_reports= 1; - } - else { - mtr_error("Unknown response: '$line' from client"); - } # Find next test to schedule # - Try to use same configuration as worker used last time @@ -805,7 +857,7 @@ sub run_test_server ($$$) { last unless defined $t; - if (run_testcase_check_skip_test($t)){ + if (main::run_testcase_check_skip_test($t)){ # Move the test to completed list #mtr_report("skip - Moving test $i to completed"); push(@$completed, splice(@$tests, $i, 1)); @@ -851,7 +903,7 @@ sub run_test_server ($$$) { # At this point we have found next suitable test $next= splice(@$tests, $i, 1); last; - } + } # for(my $i= 0; $i <= @$tests; $i++) # Use second best choice if no other test has been found if (!$next and defined $second_best){ @@ -870,11 +922,11 @@ sub run_test_server ($$$) { } else { # No more test, tell child to exit - #mtr_report("Saying BYE to child"); + mtr_verbose2("Saying BYE to ". $names{$sock}); print $sock "BYE\n"; - } - } - } + } # else (!$next) + } # else ($sock != $server) + } # foreach my $sock (@ready) if (!IS_WINDOWS) { foreach my $pid (keys %$children) @@ -906,7 +958,7 @@ sub run_test_server ($$$) { # ---------------------------------------------------- # Check if test suite timer expired # ---------------------------------------------------- - if ( has_expired($suite_timeout) ) + if ( main::has_expired($suite_timeout) ) { mtr_report("Test suite timeout! Terminating..."); return ("Timeout", 1, $completed, $extra_warnings); @@ -914,6 +966,9 @@ sub run_test_server ($$$) { } } +1; + +package main; sub run_worker ($) { my ($server_port, $thread_num)= @_; @@ -934,7 +989,10 @@ sub run_worker ($) { # -------------------------------------------------------------------------- # Set worker name # -------------------------------------------------------------------------- - report_option('name',"worker[$thread_num]"); + report_option('name',"worker[". sprintf("%02d", $thread_num). "]"); + my $proc_title= basename($0). " ${mtr_report::name} :". $server->sockport(). " -> :${server_port}"; + $0= $proc_title; + mtr_verbose2("Running at PID $$"); # -------------------------------------------------------------------------- # Set different ports per thread @@ -960,7 +1018,7 @@ sub run_worker ($) { } # Ask server for first test - print $server "START\n"; + print $server "START ${mtr_report::name}\n"; mark_time_used('init'); @@ -968,6 +1026,7 @@ sub run_worker ($) { chomp($line); if ($line eq 'TESTCASE'){ my $test= My::Test::read_test($server); + $0= $proc_title. " ". $test->{name}; # Clear comment and logfile, to avoid # reusing them from previous test @@ -984,11 +1043,12 @@ sub run_worker ($) { run_testcase($test, $server); #$test->{result}= 'MTR_RES_PASSED'; # Send it back, now with results set + mtr_verbose2('Writing TESTRESULT'); $test->write_test($server, 'TESTRESULT'); mark_time_used('restart'); } elsif ($line eq 'BYE'){ - mtr_report("Server said BYE"); + mtr_verbose2("Manager said BYE"); # We need to gracefully shut down the servers to see any # Valgrind memory leak errors etc. since last server restart. if ($opt_warnings) { @@ -1217,7 +1277,8 @@ sub command_line_setup { 'xml-report=s' => \$opt_xml_report, My::Debugger::options(), - My::CoreDump::options() + My::CoreDump::options(), + My::Platform::options() ); # fix options (that take an optional argument and *only* after = sign @@ -1253,6 +1314,9 @@ sub command_line_setup { } if (IS_CYGWIN) { + if (My::Platform::check_cygwin_subshell()) { + die("Cygwin /bin/sh subshell requires fix with --cygwin-subshell-fix=do\n"); + } # Use mixed path format i.e c:/path/to/ $glob_mysql_test_dir= mixed_path($glob_mysql_test_dir); } @@ -1748,11 +1812,12 @@ sub collect_mysqld_features { # to simplify the parsing, we'll merge all nicely formatted --help texts $list =~ s/\n {22}(\S)/ $1/g; - my @list= split '\n', $list; + my @list= split '\R', $list; $mysql_version_id= 0; + my $exe= basename($exe_mysqld); while (defined(my $line = shift @list)){ - if ($line =~ /^\Q$exe_mysqld\E\s+Ver\s(\d+)\.(\d+)\.(\d+)(\S*)/ ) { + if ($line =~ /\W\Q$exe\E\s+Ver\s(\d+)\.(\d+)\.(\d+)(\S*)/ ) { $mysql_version_id= $1*10000 + $2*100 + $3; mtr_report("MariaDB Version $1.$2.$3$4"); last; @@ -1784,7 +1849,7 @@ sub collect_mysqld_features { next; } - last if /^$/; # then goes a list of variables, it ends with an empty line + last if /^\r?$/; # then goes a list of variables, it ends with an empty line # Put a variable into hash /^([\S]+)[ \t]+(.*?)\r?$/ or die "Could not parse mysqld --help: $_\n"; @@ -1815,7 +1880,7 @@ sub collect_mysqld_features_from_running_server () my $list = `$cmd` or mtr_error("Could not connect to extern server using command: '$cmd'"); - foreach my $line (split('\n', $list )) + foreach my $line (split('\R', $list )) { # Put variables into hash if ( $line =~ /^([\S]+)[ \t]+(.*?)\r?$/ ) @@ -1906,7 +1971,7 @@ sub client_debug_arg($$) { if ( $opt_debug ) { mtr_add_arg($args, - "--loose-debug-dbug=$debug_d:t:A,%s/log/%s.trace", + "--loose-debug-dbug=d,info,warning,warnings:t:A,%s/log/%s.trace", $path_vardir_trace, $client_name) } } @@ -2959,7 +3024,7 @@ sub initialize_servers { # sub sql_to_bootstrap { my ($sql) = @_; - my @lines= split(/\n/, $sql); + my @lines= split(/\R/, $sql); my $result= "\n"; my $delimiter= ';'; @@ -4118,9 +4183,8 @@ sub run_testcase ($$) { } return ($res == 62) ? 0 : $res; - } - - if ($proc) + } # if ($proc and $proc eq $test) + elsif ($proc) { # It was not mysqltest that exited, add to a wait-to-be-started-again list. $keep_waiting_proc{$proc} = 1; @@ -4149,7 +4213,7 @@ sub run_testcase ($$) { { # do nothing } - } + } # foreach my $wait_for_proc next; @@ -5547,7 +5611,11 @@ sub start_mysqltest ($) { mtr_init_args(\$args); mtr_add_arg($args, "--defaults-file=%s", $path_config_file); - mtr_add_arg($args, "--silent"); + if ($opt_verbose > 1) { + mtr_add_arg($args, "--verbose"); + } else { + mtr_add_arg($args, "--silent"); + } mtr_add_arg($args, "--tmpdir=%s", $opt_tmpdir); mtr_add_arg($args, "--character-sets-dir=%s", $path_charsetsdir); mtr_add_arg($args, "--logdir=%s/log", $opt_vardir); diff --git a/mysql-test/suite/archive/archive.test b/mysql-test/suite/archive/archive.test index df5f6503321..c968ed1e138 100644 --- a/mysql-test/suite/archive/archive.test +++ b/mysql-test/suite/archive/archive.test @@ -1609,6 +1609,8 @@ CREATE TABLE t1(a INT, b BLOB) ENGINE=archive; SELECT DATA_LENGTH, AVG_ROW_LENGTH FROM INFORMATION_SCHEMA.TABLES WHERE TABLE_NAME='t1' AND TABLE_SCHEMA='test'; INSERT INTO t1 VALUES(1, 'sampleblob1'),(2, 'sampleblob2'); +# Compression length depends on zip library +--replace_result 583 584 291 292 SELECT DATA_LENGTH, AVG_ROW_LENGTH FROM INFORMATION_SCHEMA.TABLES WHERE TABLE_NAME='t1' AND TABLE_SCHEMA='test'; DROP TABLE t1; diff --git a/mysql-test/suite/binlog/r/binlog_empty_xa_prepared.result b/mysql-test/suite/binlog/r/binlog_empty_xa_prepared.result index b11484367b8..4625a6cab21 100644 --- a/mysql-test/suite/binlog/r/binlog_empty_xa_prepared.result +++ b/mysql-test/suite/binlog/r/binlog_empty_xa_prepared.result @@ -217,3 +217,11 @@ master-bin.000001 # Gtid # # BEGIN GTID #-#-# master-bin.000001 # Query # # use `test`; INSERT INTO tm VALUES (1),(1) master-bin.000001 # Query # # COMMIT DROP TABLE tm; +connection default; +SET pseudo_slave_mode=1; +XA START 'a'; +XA END 'a'; +XA PREPARE 'a'; +XA ROLLBACK 'a'; +ERROR XA100: XA_RBROLLBACK: Transaction branch was rolled back +include/show_binlog_events.inc diff --git a/mysql-test/suite/binlog/t/binlog_empty_xa_prepared.test b/mysql-test/suite/binlog/t/binlog_empty_xa_prepared.test index 52b4ad2037b..501403f46fc 100644 --- a/mysql-test/suite/binlog/t/binlog_empty_xa_prepared.test +++ b/mysql-test/suite/binlog/t/binlog_empty_xa_prepared.test @@ -134,3 +134,15 @@ XA ROLLBACK '1'; --source include/show_binlog_events.inc DROP TABLE tm; + +# MDEV-32257 dangling XA-rollback in binlog from emtpy XA +--connection default +--let $binlog_start = query_get_value(SHOW MASTER STATUS, Position, 1) +--let $binlog_file = query_get_value(SHOW MASTER STATUS, File, 1) +SET pseudo_slave_mode=1; +XA START 'a'; +XA END 'a'; +XA PREPARE 'a'; +--error ER_XA_RBROLLBACK +XA ROLLBACK 'a'; +--source include/show_binlog_events.inc diff --git a/mysql-test/suite/compat/oracle/t/column_compression.test b/mysql-test/suite/compat/oracle/t/column_compression.test index 6fcdd119890..01d4977ba96 100644 --- a/mysql-test/suite/compat/oracle/t/column_compression.test +++ b/mysql-test/suite/compat/oracle/t/column_compression.test @@ -1,5 +1,6 @@ --source include/have_innodb.inc --source include/have_csv.inc +--source include/have_normal_bzip.inc SET sql_mode=ORACLE; diff --git a/mysql-test/suite/encryption/r/innodb-page_encryption-32k.result b/mysql-test/suite/encryption/r/innodb-page_encryption-32k.result index 72cd3e08931..fc49d8313f5 100644 --- a/mysql-test/suite/encryption/r/innodb-page_encryption-32k.result +++ b/mysql-test/suite/encryption/r/innodb-page_encryption-32k.result @@ -14,19 +14,19 @@ Table Create Table innodb_compact CREATE TABLE `innodb_compact` ( `c1` bigint(20) NOT NULL, `b` char(200) DEFAULT NULL -) ENGINE=InnoDB DEFAULT CHARSET=latin1 ROW_FORMAT=COMPACT `encrypted`=yes `encryption_key_id`=1 +) ENGINE=InnoDB DEFAULT CHARSET=latin1 COLLATE=latin1_swedish_ci ROW_FORMAT=COMPACT `encrypted`=yes `encryption_key_id`=1 show create table innodb_dynamic; Table Create Table innodb_dynamic CREATE TABLE `innodb_dynamic` ( `c1` bigint(20) NOT NULL, `b` char(200) DEFAULT NULL -) ENGINE=InnoDB DEFAULT CHARSET=latin1 ROW_FORMAT=DYNAMIC `encrypted`=yes `encryption_key_id`=33 +) ENGINE=InnoDB DEFAULT CHARSET=latin1 COLLATE=latin1_swedish_ci ROW_FORMAT=DYNAMIC `encrypted`=yes `encryption_key_id`=33 show create table innodb_redundant; Table Create Table innodb_redundant CREATE TABLE `innodb_redundant` ( `c1` bigint(20) NOT NULL, `b` char(200) DEFAULT NULL -) ENGINE=InnoDB DEFAULT CHARSET=latin1 ROW_FORMAT=REDUNDANT `encrypted`=yes `encryption_key_id`=4 +) ENGINE=InnoDB DEFAULT CHARSET=latin1 COLLATE=latin1_swedish_ci ROW_FORMAT=REDUNDANT `encrypted`=yes `encryption_key_id`=4 create procedure innodb_insert_proc (repeat_count int) begin declare current_num int; @@ -56,6 +56,7 @@ count(*) select count(*) from innodb_redundant where c1 < 1500000; count(*) 5000 +# restart update innodb_compact set c1 = c1 + 1; update innodb_dynamic set c1 = c1 + 1; update innodb_redundant set c1 = c1 + 1; @@ -74,39 +75,40 @@ Table Create Table innodb_compact CREATE TABLE `innodb_compact` ( `c1` bigint(20) NOT NULL, `b` char(200) DEFAULT NULL -) ENGINE=InnoDB DEFAULT CHARSET=latin1 ROW_FORMAT=COMPACT +) ENGINE=InnoDB DEFAULT CHARSET=latin1 COLLATE=latin1_swedish_ci ROW_FORMAT=COMPACT alter table innodb_dynamic engine=innodb encrypted=DEFAULT encryption_key_id=DEFAULT; show create table innodb_dynamic; Table Create Table innodb_dynamic CREATE TABLE `innodb_dynamic` ( `c1` bigint(20) NOT NULL, `b` char(200) DEFAULT NULL -) ENGINE=InnoDB DEFAULT CHARSET=latin1 ROW_FORMAT=DYNAMIC +) ENGINE=InnoDB DEFAULT CHARSET=latin1 COLLATE=latin1_swedish_ci ROW_FORMAT=DYNAMIC alter table innodb_redundant engine=innodb encrypted=DEFAULT encryption_key_id=DEFAULT; show create table innodb_redundant; Table Create Table innodb_redundant CREATE TABLE `innodb_redundant` ( `c1` bigint(20) NOT NULL, `b` char(200) DEFAULT NULL -) ENGINE=InnoDB DEFAULT CHARSET=latin1 ROW_FORMAT=REDUNDANT +) ENGINE=InnoDB DEFAULT CHARSET=latin1 COLLATE=latin1_swedish_ci ROW_FORMAT=REDUNDANT +# restart show create table innodb_compact; Table Create Table innodb_compact CREATE TABLE `innodb_compact` ( `c1` bigint(20) NOT NULL, `b` char(200) DEFAULT NULL -) ENGINE=InnoDB DEFAULT CHARSET=latin1 ROW_FORMAT=COMPACT +) ENGINE=InnoDB DEFAULT CHARSET=latin1 COLLATE=latin1_swedish_ci ROW_FORMAT=COMPACT show create table innodb_dynamic; Table Create Table innodb_dynamic CREATE TABLE `innodb_dynamic` ( `c1` bigint(20) NOT NULL, `b` char(200) DEFAULT NULL -) ENGINE=InnoDB DEFAULT CHARSET=latin1 ROW_FORMAT=DYNAMIC +) ENGINE=InnoDB DEFAULT CHARSET=latin1 COLLATE=latin1_swedish_ci ROW_FORMAT=DYNAMIC show create table innodb_redundant; Table Create Table innodb_redundant CREATE TABLE `innodb_redundant` ( `c1` bigint(20) NOT NULL, `b` char(200) DEFAULT NULL -) ENGINE=InnoDB DEFAULT CHARSET=latin1 ROW_FORMAT=REDUNDANT +) ENGINE=InnoDB DEFAULT CHARSET=latin1 COLLATE=latin1_swedish_ci ROW_FORMAT=REDUNDANT update innodb_compact set c1 = c1 + 1; update innodb_dynamic set c1 = c1 + 1; update innodb_redundant set c1 = c1 + 1; diff --git a/mysql-test/suite/encryption/r/innodb-redo-nokeys.result b/mysql-test/suite/encryption/r/innodb-redo-nokeys.result index 6482a5d960d..e503cb9a95c 100644 --- a/mysql-test/suite/encryption/r/innodb-redo-nokeys.result +++ b/mysql-test/suite/encryption/r/innodb-redo-nokeys.result @@ -11,6 +11,7 @@ call mtr.add_suppression("InnoDB: OPT_PAGE_CHECKSUM mismatch"); call mtr.add_suppression("InnoDB: Missing FILE_CHECKPOINT"); call mtr.add_suppression("InnoDB: Log scan aborted at LSN"); call mtr.add_suppression("InnoDB: Set innodb_force_recovery=1 to ignore corruption"); +call mtr.add_suppression("InnoDB: Encryption key is not found for"); # restart: --file-key-management-filename=MYSQL_TEST_DIR/std_data/keys2.txt create table t1(a int not null primary key auto_increment, c char(200), b blob, index(b(10))) engine=innodb row_format=compressed encrypted=yes encryption_key_id=20; create table t2(a int not null primary key auto_increment, c char(200), b blob, index(b(10))) engine=innodb row_format=compressed encrypted=yes; @@ -40,5 +41,6 @@ SELECT * FROM INFORMATION_SCHEMA.ENGINES WHERE engine = 'innodb' AND support IN ('YES', 'DEFAULT', 'ENABLED'); ENGINE SUPPORT COMMENT TRANSACTIONS XA SAVEPOINTS +FOUND 1 /\[ERROR\] InnoDB: Encryption key is not found for .*test.t1.ibd/ in mysqld.1.err # restart: --file-key-management-filename=MYSQL_TEST_DIR/std_data/keys2.txt drop table t1,t2,t3,t4,t5; diff --git a/mysql-test/suite/encryption/t/innodb-redo-nokeys.test b/mysql-test/suite/encryption/t/innodb-redo-nokeys.test index 1eca1d8cf73..22fcd75446e 100644 --- a/mysql-test/suite/encryption/t/innodb-redo-nokeys.test +++ b/mysql-test/suite/encryption/t/innodb-redo-nokeys.test @@ -16,6 +16,7 @@ call mtr.add_suppression("InnoDB: OPT_PAGE_CHECKSUM mismatch"); call mtr.add_suppression("InnoDB: Missing FILE_CHECKPOINT"); call mtr.add_suppression("InnoDB: Log scan aborted at LSN"); call mtr.add_suppression("InnoDB: Set innodb_force_recovery=1 to ignore corruption"); +call mtr.add_suppression("InnoDB: Encryption key is not found for"); -- let $restart_parameters=--file-key-management-filename=$MYSQL_TEST_DIR/std_data/keys2.txt -- source include/restart_mysqld.inc @@ -73,6 +74,10 @@ SELECT * FROM INFORMATION_SCHEMA.ENGINES WHERE engine = 'innodb' AND support IN ('YES', 'DEFAULT', 'ENABLED'); +let SEARCH_FILE = $MYSQLTEST_VARDIR/log/mysqld.1.err; +let SEARCH_PATTERN = \[ERROR\] InnoDB: Encryption key is not found for .*test.t1.ibd; +--source include/search_pattern_in_file.inc + # # In above server does start but InnoDB refuses to start # thus we need to restart server with correct key file diff --git a/mysql-test/suite/events/events_grant.result b/mysql-test/suite/events/events_grant.result index 5952097a8d2..6441d7b3f58 100644 --- a/mysql-test/suite/events/events_grant.result +++ b/mysql-test/suite/events/events_grant.result @@ -27,7 +27,7 @@ Grants for ev_test@localhost GRANT USAGE ON *.* TO `ev_test`@`localhost` GRANT ALL PRIVILEGES ON `test`.* TO `ev_test`@`localhost` GRANT ALL PRIVILEGES ON `events_test`.* TO `ev_test`@`localhost` -GRANT SELECT, INSERT, UPDATE, DELETE, CREATE, DROP, REFERENCES, INDEX, ALTER, CREATE TEMPORARY TABLES, LOCK TABLES, EXECUTE, CREATE VIEW, SHOW VIEW, CREATE ROUTINE, ALTER ROUTINE, TRIGGER, DELETE HISTORY ON `events_test2`.* TO `ev_test`@`localhost` +GRANT SELECT, INSERT, UPDATE, DELETE, CREATE, DROP, REFERENCES, INDEX, ALTER, CREATE TEMPORARY TABLES, LOCK TABLES, EXECUTE, CREATE VIEW, SHOW VIEW, CREATE ROUTINE, ALTER ROUTINE, TRIGGER, DELETE HISTORY, SHOW CREATE ROUTINE ON `events_test2`.* TO `ev_test`@`localhost` "Here comes an error:"; SHOW EVENTS; ERROR 42000: Access denied for user 'ev_test'@'localhost' to database 'events_test2' diff --git a/mysql-test/suite/funcs_1/datadict/processlist_priv.inc b/mysql-test/suite/funcs_1/datadict/processlist_priv.inc index 90bc19f2784..298a026ed77 100644 --- a/mysql-test/suite/funcs_1/datadict/processlist_priv.inc +++ b/mysql-test/suite/funcs_1/datadict/processlist_priv.inc @@ -161,7 +161,7 @@ eval SHOW CREATE TABLE $table; --replace_result Execute Query --replace_column 1 ID 3 HOST_NAME 6 TIME 9 TIME_MS eval SHOW $table; ---replace_column 1 ID 3 HOST_NAME 6 TIME 9 TIME_MS 13 MEMORY 14 MAX_MEMORY 15 ROWS 16 QUERY_ID 18 TID +--replace_column 1 ID 3 HOST_NAME 6 TIME 9 TIME_MS 13 MEMORY 14 MAX_MEMORY 15 E_ROWS 16 S_ROWS 17 QUERY_ID 19 TID eval SELECT * FROM $table $select_where ORDER BY id; --replace_column 1 ID 3 HOST_NAME 6 TIME 9 TIME_MS 13 MEMORY 14 ROWS 15 QUERY_ID 17 TID eval SELECT $columns FROM $table $select_where ORDER BY id; @@ -182,7 +182,7 @@ eval SHOW CREATE TABLE $table; --replace_result Execute Query --replace_column 1 ID 3 HOST_NAME 6 TIME 9 TIME_MS eval SHOW $table; ---replace_column 1 ID 3 HOST_NAME 6 TIME 9 TIME_MS 13 MEMORY 14 MAX_MEMORY 15 ROWS 16 QUERY_ID 18 TID +--replace_column 1 ID 3 HOST_NAME 6 TIME 9 TIME_MS 13 MEMORY 14 MAX_MEMORY 15 E_ROWS 16 S_ROWS 17 QUERY_ID 19 TID eval SELECT * FROM $table $select_where ORDER BY id; --replace_column 1 ID 3 HOST_NAME 6 TIME 9 TIME_MS 13 MEMORY 14 ROWS 15 QUERY_ID 17 TID eval SELECT $columns FROM $table $select_where ORDER BY id; @@ -209,7 +209,7 @@ SHOW GRANTS; --replace_result Execute Query --replace_column 1 ID 3 HOST_NAME 6 TIME 9 TIME_MS SHOW processlist; ---replace_column 1 ID 3 HOST_NAME 6 TIME 9 TIME_MS 13 MEMORY 14 MAX_MEMORY 15 ROWS 16 QUERY_ID 18 TID +--replace_column 1 ID 3 HOST_NAME 6 TIME 9 TIME_MS 13 MEMORY 14 MAX_MEMORY 15 E_ROWS 16 S_ROWS 17 QUERY_ID 19 TID SELECT * FROM information_schema.processlist; --real_sleep 0.3 @@ -222,7 +222,7 @@ SHOW GRANTS; --replace_result Execute Query --replace_column 1 ID 3 HOST_NAME 6 TIME 9 TIME_MS SHOW processlist; ---replace_column 1 ID 3 HOST_NAME 6 TIME 9 TIME_MS 13 MEMORY 14 MAX_MEMORY 15 ROWS 16 QUERY_ID 18 TID +--replace_column 1 ID 3 HOST_NAME 6 TIME 9 TIME_MS 13 MEMORY 14 MAX_MEMORY 15 E_ROWS 16 S_ROWS 17 QUERY_ID 19 TID SELECT * FROM information_schema.processlist; --real_sleep 0.3 @@ -246,7 +246,7 @@ SHOW GRANTS; --replace_result Execute Query --replace_column 1 ID 3 HOST_NAME 6 TIME 9 TIME_MS SHOW processlist; ---replace_column 1 ID 3 HOST_NAME 6 TIME 9 TIME_MS 13 MEMORY 14 MAX_MEMORY 15 ROWS 16 QUERY_ID 18 TID +--replace_column 1 ID 3 HOST_NAME 6 TIME 9 TIME_MS 13 MEMORY 14 MAX_MEMORY 15 E_ROWS 16 S_ROWS 17 QUERY_ID 19 TID SELECT * FROM information_schema.processlist; --real_sleep 0.3 @@ -269,7 +269,7 @@ SHOW GRANTS; --replace_result Execute Query --replace_column 1 ID 3 HOST_NAME 6 TIME 9 TIME_MS SHOW processlist; ---replace_column 1 ID 3 HOST_NAME 6 TIME 9 TIME_MS 13 MEMORY 14 MAX_MEMORY 15 ROWS 16 QUERY_ID 18 TID +--replace_column 1 ID 3 HOST_NAME 6 TIME 9 TIME_MS 13 MEMORY 14 MAX_MEMORY 15 E_ROWS 16 S_ROWS 17 QUERY_ID 19 TID SELECT * FROM information_schema.processlist; --real_sleep 0.3 @@ -296,7 +296,7 @@ if ($fixed_bug_30395) --replace_column 1 ID 3 HOST_NAME 6 TIME 9 TIME_MS SHOW processlist; } ---replace_column 1 ID 3 HOST_NAME 6 TIME 9 TIME_MS 13 MEMORY 14 MAX_MEMORY 15 ROWS 16 QUERY_ID 18 TID +--replace_column 1 ID 3 HOST_NAME 6 TIME 9 TIME_MS 13 MEMORY 14 MAX_MEMORY 15 E_ROWS 16 S_ROWS 17 QUERY_ID 19 TID SELECT * FROM information_schema.processlist; --real_sleep 0.3 @@ -318,7 +318,7 @@ SHOW GRANTS FOR 'ddicttestuser1'@'localhost'; --replace_result Execute Query --replace_column 1 ID 3 HOST_NAME 6 TIME 9 TIME_MS SHOW processlist; ---replace_column 1 ID 3 HOST_NAME 6 TIME 9 TIME_MS 13 MEMORY 14 MAX_MEMORY 15 ROWS 16 QUERY_ID 18 TID +--replace_column 1 ID 3 HOST_NAME 6 TIME 9 TIME_MS 13 MEMORY 14 MAX_MEMORY 15 E_ROWS 16 S_ROWS 17 QUERY_ID 19 TID SELECT * FROM information_schema.processlist; --real_sleep 0.3 @@ -341,7 +341,7 @@ SHOW GRANTS FOR 'ddicttestuser1'@'localhost'; --replace_result Execute Query --replace_column 1 ID 3 HOST_NAME 6 TIME 9 TIME_MS SHOW processlist; ---replace_column 1 ID 3 HOST_NAME 6 TIME 9 TIME_MS 13 MEMORY 14 MAX_MEMORY 15 ROWS 16 QUERY_ID 18 TID +--replace_column 1 ID 3 HOST_NAME 6 TIME 9 TIME_MS 13 MEMORY 14 MAX_MEMORY 15 E_ROWS 16 S_ROWS 17 QUERY_ID 19 TID SELECT * FROM information_schema.processlist; --real_sleep 0.3 @@ -389,7 +389,7 @@ SHOW GRANTS FOR 'ddicttestuser2'@'localhost'; --replace_result Execute Query --replace_column 1 ID 3 HOST_NAME 6 TIME 9 TIME_MS SHOW processlist; ---replace_column 1 ID 3 HOST_NAME 6 TIME 9 TIME_MS 13 MEMORY 14 MAX_MEMORY 15 ROWS 16 QUERY_ID 18 TID +--replace_column 1 ID 3 HOST_NAME 6 TIME 9 TIME_MS 13 MEMORY 14 MAX_MEMORY 15 E_ROWS 16 S_ROWS 17 QUERY_ID 19 TID SELECT * FROM information_schema.processlist; --real_sleep 0.3 @@ -411,7 +411,7 @@ SHOW GRANTS; --replace_result Execute Query --replace_column 1 ID 3 HOST_NAME 6 TIME 9 TIME_MS SHOW processlist; ---replace_column 1 ID 3 HOST_NAME 6 TIME 9 TIME_MS 13 MEMORY 14 MAX_MEMORY 15 ROWS 16 QUERY_ID 18 TID +--replace_column 1 ID 3 HOST_NAME 6 TIME 9 TIME_MS 13 MEMORY 14 MAX_MEMORY 15 E_ROWS 16 S_ROWS 17 QUERY_ID 19 TID SELECT * FROM information_schema.processlist; --real_sleep 0.3 @@ -435,7 +435,7 @@ GRANT PROCESS ON *.* TO 'ddicttestuser2'@'localhost'; --replace_result Execute Query --replace_column 1 ID 3 HOST_NAME 6 TIME 9 TIME_MS SHOW processlist; ---replace_column 1 ID 3 HOST_NAME 6 TIME 9 TIME_MS 13 MEMORY 14 MAX_MEMORY 15 ROWS 16 QUERY_ID 18 TID +--replace_column 1 ID 3 HOST_NAME 6 TIME 9 TIME_MS 13 MEMORY 14 MAX_MEMORY 15 E_ROWS 16 S_ROWS 17 QUERY_ID 19 TID SELECT * FROM information_schema.processlist; --real_sleep 0.3 @@ -460,7 +460,7 @@ SHOW GRANTS FOR 'ddicttestuser1'@'localhost'; --replace_result Execute Query --replace_column 1 ID 3 HOST_NAME 6 TIME 9 TIME_MS SHOW processlist; ---replace_column 1 ID 3 HOST_NAME 6 TIME 9 TIME_MS 13 MEMORY 14 MAX_MEMORY 15 ROWS 16 QUERY_ID 18 TID +--replace_column 1 ID 3 HOST_NAME 6 TIME 9 TIME_MS 13 MEMORY 14 MAX_MEMORY 15 E_ROWS 16 S_ROWS 17 QUERY_ID 19 TID SELECT * FROM information_schema.processlist; --real_sleep 0.3 diff --git a/mysql-test/suite/funcs_1/datadict/processlist_val.inc b/mysql-test/suite/funcs_1/datadict/processlist_val.inc index fa6ed4049d6..ab2482393d5 100644 --- a/mysql-test/suite/funcs_1/datadict/processlist_val.inc +++ b/mysql-test/suite/funcs_1/datadict/processlist_val.inc @@ -92,7 +92,7 @@ echo # - INFO must contain the corresponding SHOW/SELECT PROCESSLIST # # 1. Just dump what we get ---replace_column 1 3 6
a"; - - all = div.getElementsByTagName( "*" ); - a = div.getElementsByTagName( "a" )[ 0 ]; - - // Can't get basic test support - if ( !all || !all.length || !a ) { - return {}; - } - - // First batch of supports tests - select = document.createElement( "select" ); - opt = select.appendChild( document.createElement("option") ); - input = div.getElementsByTagName( "input" )[ 0 ]; - - support = { - // IE strips leading whitespace when .innerHTML is used - leadingWhitespace: ( div.firstChild.nodeType === 3 ), - - // Make sure that tbody elements aren't automatically inserted - // IE will insert them into empty tables - tbody: !div.getElementsByTagName("tbody").length, - - // Make sure that link elements get serialized correctly by innerHTML - // This requires a wrapper element in IE - htmlSerialize: !!div.getElementsByTagName("link").length, - - // Get the style information from getAttribute - // (IE uses .cssText instead) - style: /top/.test( a.getAttribute("style") ), - - // Make sure that URLs aren't manipulated - // (IE normalizes it by default) - hrefNormalized: ( a.getAttribute("href") === "/a" ), - - // Make sure that element opacity exists - // (IE uses filter instead) - // Use a regex to work around a WebKit issue. See #5145 - opacity: /^0.55/.test( a.style.opacity ), - - // Verify style float existence - // (IE uses styleFloat instead of cssFloat) - cssFloat: !!a.style.cssFloat, - - // Make sure that if no value is specified for a checkbox - // that it defaults to "on". - // (WebKit defaults to "" instead) - checkOn: ( input.value === "on" ), - - // Make sure that a selected-by-default option has a working selected property. - // (WebKit defaults to false instead of true, IE too, if it's in an optgroup) - optSelected: opt.selected, - - // Test setAttribute on camelCase class. If it works, we need attrFixes when doing get/setAttribute (ie6/7) - getSetAttribute: div.className !== "t", - - // Tests for enctype support on a form(#6743) - enctype: !!document.createElement("form").enctype, - - // Makes sure cloning an html5 element does not cause problems - // Where outerHTML is undefined, this still works - html5Clone: document.createElement("nav").cloneNode( true ).outerHTML !== "<:nav>", - - // Will be defined later - submitBubbles: true, - changeBubbles: true, - focusinBubbles: false, - deleteExpando: true, - noCloneEvent: true, - inlineBlockNeedsLayout: false, - shrinkWrapBlocks: false, - reliableMarginRight: true, - pixelMargin: true - }; - - // jQuery.boxModel DEPRECATED in 1.3, use jQuery.support.boxModel instead - jQuery.boxModel = support.boxModel = (document.compatMode === "CSS1Compat"); - - // Make sure checked status is properly cloned - input.checked = true; - support.noCloneChecked = input.cloneNode( true ).checked; - - // Make sure that the options inside disabled selects aren't marked as disabled - // (WebKit marks them as disabled) - select.disabled = true; - support.optDisabled = !opt.disabled; - - // Test to see if it's possible to delete an expando from an element - // Fails in Internet Explorer - try { - delete div.test; - } catch( e ) { - support.deleteExpando = false; - } - - if ( !div.addEventListener && div.attachEvent && div.fireEvent ) { - div.attachEvent( "onclick", function() { - // Cloning a node shouldn't copy over any - // bound event handlers (IE does this) - support.noCloneEvent = false; - }); - div.cloneNode( true ).fireEvent( "onclick" ); - } - - // Check if a radio maintains its value - // after being appended to the DOM - input = document.createElement("input"); - input.value = "t"; - input.setAttribute("type", "radio"); - support.radioValue = input.value === "t"; - - input.setAttribute("checked", "checked"); - - // #11217 - WebKit loses check when the name is after the checked attribute - input.setAttribute( "name", "t" ); - - div.appendChild( input ); - fragment = document.createDocumentFragment(); - fragment.appendChild( div.lastChild ); - - // WebKit doesn't clone checked state correctly in fragments - support.checkClone = fragment.cloneNode( true ).cloneNode( true ).lastChild.checked; - - // Check if a disconnected checkbox will retain its checked - // value of true after appended to the DOM (IE6/7) - support.appendChecked = input.checked; - - fragment.removeChild( input ); - fragment.appendChild( div ); - - // Technique from Juriy Zaytsev - // http://perfectionkills.com/detecting-event-support-without-browser-sniffing/ - // We only care about the case where non-standard event systems - // are used, namely in IE. Short-circuiting here helps us to - // avoid an eval call (in setAttribute) which can cause CSP - // to go haywire. See: https://developer.mozilla.org/en/Security/CSP - if ( div.attachEvent ) { - for ( i in { - submit: 1, - change: 1, - focusin: 1 - }) { - eventName = "on" + i; - isSupported = ( eventName in div ); - if ( !isSupported ) { - div.setAttribute( eventName, "return;" ); - isSupported = ( typeof div[ eventName ] === "function" ); - } - support[ i + "Bubbles" ] = isSupported; - } - } - - fragment.removeChild( div ); - - // Null elements to avoid leaks in IE - fragment = select = opt = div = input = null; - - // Run tests that need a body at doc ready - jQuery(function() { - var container, outer, inner, table, td, offsetSupport, - marginDiv, conMarginTop, style, html, positionTopLeftWidthHeight, - paddingMarginBorderVisibility, paddingMarginBorder, - body = document.getElementsByTagName("body")[0]; - - if ( !body ) { - // Return for frameset docs that don't have a body - return; - } - - conMarginTop = 1; - paddingMarginBorder = "padding:0;margin:0;border:"; - positionTopLeftWidthHeight = "position:absolute;top:0;left:0;width:1px;height:1px;"; - paddingMarginBorderVisibility = paddingMarginBorder + "0;visibility:hidden;"; - style = "style='" + positionTopLeftWidthHeight + paddingMarginBorder + "5px solid #000;"; - html = "
" + - "" + - "
"; - - container = document.createElement("div"); - container.style.cssText = paddingMarginBorderVisibility + "width:0;height:0;position:static;top:0;margin-top:" + conMarginTop + "px"; - body.insertBefore( container, body.firstChild ); - - // Construct the test element - div = document.createElement("div"); - container.appendChild( div ); - - // Check if table cells still have offsetWidth/Height when they are set - // to display:none and there are still other visible table cells in a - // table row; if so, offsetWidth/Height are not reliable for use when - // determining if an element has been hidden directly using - // display:none (it is still safe to use offsets if a parent element is - // hidden; don safety goggles and see bug #4512 for more information). - // (only IE 8 fails this test) - div.innerHTML = "
t
"; - tds = div.getElementsByTagName( "td" ); - isSupported = ( tds[ 0 ].offsetHeight === 0 ); - - tds[ 0 ].style.display = ""; - tds[ 1 ].style.display = "none"; - - // Check if empty table cells still have offsetWidth/Height - // (IE <= 8 fail this test) - support.reliableHiddenOffsets = isSupported && ( tds[ 0 ].offsetHeight === 0 ); - - // Check if div with explicit width and no margin-right incorrectly - // gets computed margin-right based on width of container. For more - // info see bug #3333 - // Fails in WebKit before Feb 2011 nightlies - // WebKit Bug 13343 - getComputedStyle returns wrong value for margin-right - if ( window.getComputedStyle ) { - div.innerHTML = ""; - marginDiv = document.createElement( "div" ); - marginDiv.style.width = "0"; - marginDiv.style.marginRight = "0"; - div.style.width = "2px"; - div.appendChild( marginDiv ); - support.reliableMarginRight = - ( parseInt( ( window.getComputedStyle( marginDiv, null ) || { marginRight: 0 } ).marginRight, 10 ) || 0 ) === 0; - } - - if ( typeof div.style.zoom !== "undefined" ) { - // Check if natively block-level elements act like inline-block - // elements when setting their display to 'inline' and giving - // them layout - // (IE < 8 does this) - div.innerHTML = ""; - div.style.width = div.style.padding = "1px"; - div.style.border = 0; - div.style.overflow = "hidden"; - div.style.display = "inline"; - div.style.zoom = 1; - support.inlineBlockNeedsLayout = ( div.offsetWidth === 3 ); - - // Check if elements with layout shrink-wrap their children - // (IE 6 does this) - div.style.display = "block"; - div.style.overflow = "visible"; - div.innerHTML = "
"; - support.shrinkWrapBlocks = ( div.offsetWidth !== 3 ); - } - - div.style.cssText = positionTopLeftWidthHeight + paddingMarginBorderVisibility; - div.innerHTML = html; - - outer = div.firstChild; - inner = outer.firstChild; - td = outer.nextSibling.firstChild.firstChild; - - offsetSupport = { - doesNotAddBorder: ( inner.offsetTop !== 5 ), - doesAddBorderForTableAndCells: ( td.offsetTop === 5 ) - }; - - inner.style.position = "fixed"; - inner.style.top = "20px"; - - // safari subtracts parent border width here which is 5px - offsetSupport.fixedPosition = ( inner.offsetTop === 20 || inner.offsetTop === 15 ); - inner.style.position = inner.style.top = ""; - - outer.style.overflow = "hidden"; - outer.style.position = "relative"; - - offsetSupport.subtractsBorderForOverflowNotVisible = ( inner.offsetTop === -5 ); - offsetSupport.doesNotIncludeMarginInBodyOffset = ( body.offsetTop !== conMarginTop ); - - if ( window.getComputedStyle ) { - div.style.marginTop = "1%"; - support.pixelMargin = ( window.getComputedStyle( div, null ) || { marginTop: 0 } ).marginTop !== "1%"; - } - - if ( typeof container.style.zoom !== "undefined" ) { - container.style.zoom = 1; - } - - body.removeChild( container ); - marginDiv = div = container = null; - - jQuery.extend( support, offsetSupport ); - }); - - return support; -})(); - - - - -var rbrace = /^(?:\{.*\}|\[.*\])$/, - rmultiDash = /([A-Z])/g; - -jQuery.extend({ - cache: {}, - - // Please use with caution - uuid: 0, - - // Unique for each copy of jQuery on the page - // Non-digits removed to match rinlinejQuery - expando: "jQuery" + ( jQuery.fn.jquery + Math.random() ).replace( /\D/g, "" ), - - // The following elements throw uncatchable exceptions if you - // attempt to add expando properties to them. - noData: { - "embed": true, - // Ban all objects except for Flash (which handle expandos) - "object": "clsid:D27CDB6E-AE6D-11cf-96B8-444553540000", - "applet": true - }, - - hasData: function( elem ) { - elem = elem.nodeType ? jQuery.cache[ elem[jQuery.expando] ] : elem[ jQuery.expando ]; - return !!elem && !isEmptyDataObject( elem ); - }, - - data: function( elem, name, data, pvt /* Internal Use Only */ ) { - if ( !jQuery.acceptData( elem ) ) { - return; - } - - var privateCache, thisCache, ret, - internalKey = jQuery.expando, - getByName = typeof name === "string", - - // We have to handle DOM nodes and JS objects differently because IE6-7 - // can't GC object references properly across the DOM-JS boundary - isNode = elem.nodeType, - - // Only DOM nodes need the global jQuery cache; JS object data is - // attached directly to the object so GC can occur automatically - cache = isNode ? jQuery.cache : elem, - - // Only defining an ID for JS objects if its cache already exists allows - // the code to shortcut on the same path as a DOM node with no cache - id = isNode ? elem[ internalKey ] : elem[ internalKey ] && internalKey, - isEvents = name === "events"; - - // Avoid doing any more work than we need to when trying to get data on an - // object that has no data at all - if ( (!id || !cache[id] || (!isEvents && !pvt && !cache[id].data)) && getByName && data === undefined ) { - return; - } - - if ( !id ) { - // Only DOM nodes need a new unique ID for each element since their data - // ends up in the global cache - if ( isNode ) { - elem[ internalKey ] = id = ++jQuery.uuid; - } else { - id = internalKey; - } - } - - if ( !cache[ id ] ) { - cache[ id ] = {}; - - // Avoids exposing jQuery metadata on plain JS objects when the object - // is serialized using JSON.stringify - if ( !isNode ) { - cache[ id ].toJSON = jQuery.noop; - } - } - - // An object can be passed to jQuery.data instead of a key/value pair; this gets - // shallow copied over onto the existing cache - if ( typeof name === "object" || typeof name === "function" ) { - if ( pvt ) { - cache[ id ] = jQuery.extend( cache[ id ], name ); - } else { - cache[ id ].data = jQuery.extend( cache[ id ].data, name ); - } - } - - privateCache = thisCache = cache[ id ]; - - // jQuery data() is stored in a separate object inside the object's internal data - // cache in order to avoid key collisions between internal data and user-defined - // data. - if ( !pvt ) { - if ( !thisCache.data ) { - thisCache.data = {}; - } - - thisCache = thisCache.data; - } - - if ( data !== undefined ) { - thisCache[ jQuery.camelCase( name ) ] = data; - } - - // Users should not attempt to inspect the internal events object using jQuery.data, - // it is undocumented and subject to change. But does anyone listen? No. - if ( isEvents && !thisCache[ name ] ) { - return privateCache.events; - } - - // Check for both converted-to-camel and non-converted data property names - // If a data property was specified - if ( getByName ) { - - // First Try to find as-is property data - ret = thisCache[ name ]; - - // Test for null|undefined property data - if ( ret == null ) { - - // Try to find the camelCased property - ret = thisCache[ jQuery.camelCase( name ) ]; - } - } else { - ret = thisCache; - } - - return ret; - }, - - removeData: function( elem, name, pvt /* Internal Use Only */ ) { - if ( !jQuery.acceptData( elem ) ) { - return; - } - - var thisCache, i, l, - - // Reference to internal data cache key - internalKey = jQuery.expando, - - isNode = elem.nodeType, - - // See jQuery.data for more information - cache = isNode ? jQuery.cache : elem, - - // See jQuery.data for more information - id = isNode ? elem[ internalKey ] : internalKey; - - // If there is already no cache entry for this object, there is no - // purpose in continuing - if ( !cache[ id ] ) { - return; - } - - if ( name ) { - - thisCache = pvt ? cache[ id ] : cache[ id ].data; - - if ( thisCache ) { - - // Support array or space separated string names for data keys - if ( !jQuery.isArray( name ) ) { - - // try the string as a key before any manipulation - if ( name in thisCache ) { - name = [ name ]; - } else { - - // split the camel cased version by spaces unless a key with the spaces exists - name = jQuery.camelCase( name ); - if ( name in thisCache ) { - name = [ name ]; - } else { - name = name.split( " " ); - } - } - } - - for ( i = 0, l = name.length; i < l; i++ ) { - delete thisCache[ name[i] ]; - } - - // If there is no data left in the cache, we want to continue - // and let the cache object itself get destroyed - if ( !( pvt ? isEmptyDataObject : jQuery.isEmptyObject )( thisCache ) ) { - return; - } - } - } - - // See jQuery.data for more information - if ( !pvt ) { - delete cache[ id ].data; - - // Don't destroy the parent cache unless the internal data object - // had been the only thing left in it - if ( !isEmptyDataObject(cache[ id ]) ) { - return; - } - } - - // Browsers that fail expando deletion also refuse to delete expandos on - // the window, but it will allow it on all other JS objects; other browsers - // don't care - // Ensure that `cache` is not a window object #10080 - if ( jQuery.support.deleteExpando || !cache.setInterval ) { - delete cache[ id ]; - } else { - cache[ id ] = null; - } - - // We destroyed the cache and need to eliminate the expando on the node to avoid - // false lookups in the cache for entries that no longer exist - if ( isNode ) { - // IE does not allow us to delete expando properties from nodes, - // nor does it have a removeAttribute function on Document nodes; - // we must handle all of these cases - if ( jQuery.support.deleteExpando ) { - delete elem[ internalKey ]; - } else if ( elem.removeAttribute ) { - elem.removeAttribute( internalKey ); - } else { - elem[ internalKey ] = null; - } - } - }, - - // For internal use only. - _data: function( elem, name, data ) { - return jQuery.data( elem, name, data, true ); - }, - - // A method for determining if a DOM node can handle the data expando - acceptData: function( elem ) { - if ( elem.nodeName ) { - var match = jQuery.noData[ elem.nodeName.toLowerCase() ]; - - if ( match ) { - return !(match === true || elem.getAttribute("classid") !== match); - } - } - - return true; - } -}); - -jQuery.fn.extend({ - data: function( key, value ) { - var parts, part, attr, name, l, - elem = this[0], - i = 0, - data = null; - - // Gets all values - if ( key === undefined ) { - if ( this.length ) { - data = jQuery.data( elem ); - - if ( elem.nodeType === 1 && !jQuery._data( elem, "parsedAttrs" ) ) { - attr = elem.attributes; - for ( l = attr.length; i < l; i++ ) { - name = attr[i].name; - - if ( name.indexOf( "data-" ) === 0 ) { - name = jQuery.camelCase( name.substring(5) ); - - dataAttr( elem, name, data[ name ] ); - } - } - jQuery._data( elem, "parsedAttrs", true ); - } - } - - return data; - } - - // Sets multiple values - if ( typeof key === "object" ) { - return this.each(function() { - jQuery.data( this, key ); - }); - } - - parts = key.split( ".", 2 ); - parts[1] = parts[1] ? "." + parts[1] : ""; - part = parts[1] + "!"; - - return jQuery.access( this, function( value ) { - - if ( value === undefined ) { - data = this.triggerHandler( "getData" + part, [ parts[0] ] ); - - // Try to fetch any internally stored data first - if ( data === undefined && elem ) { - data = jQuery.data( elem, key ); - data = dataAttr( elem, key, data ); - } - - return data === undefined && parts[1] ? - this.data( parts[0] ) : - data; - } - - parts[1] = value; - this.each(function() { - var self = jQuery( this ); - - self.triggerHandler( "setData" + part, parts ); - jQuery.data( this, key, value ); - self.triggerHandler( "changeData" + part, parts ); - }); - }, null, value, arguments.length > 1, null, false ); - }, - - removeData: function( key ) { - return this.each(function() { - jQuery.removeData( this, key ); - }); - } -}); - -function dataAttr( elem, key, data ) { - // If nothing was found internally, try to fetch any - // data from the HTML5 data-* attribute - if ( data === undefined && elem.nodeType === 1 ) { - - var name = "data-" + key.replace( rmultiDash, "-$1" ).toLowerCase(); - - data = elem.getAttribute( name ); - - if ( typeof data === "string" ) { - try { - data = data === "true" ? true : - data === "false" ? false : - data === "null" ? null : - jQuery.isNumeric( data ) ? +data : - rbrace.test( data ) ? jQuery.parseJSON( data ) : - data; - } catch( e ) {} - - // Make sure we set the data so it isn't changed later - jQuery.data( elem, key, data ); - - } else { - data = undefined; - } - } - - return data; -} - -// checks a cache object for emptiness -function isEmptyDataObject( obj ) { - for ( var name in obj ) { - - // if the public data object is empty, the private is still empty - if ( name === "data" && jQuery.isEmptyObject( obj[name] ) ) { - continue; - } - if ( name !== "toJSON" ) { - return false; - } - } - - return true; -} - - - - -function handleQueueMarkDefer( elem, type, src ) { - var deferDataKey = type + "defer", - queueDataKey = type + "queue", - markDataKey = type + "mark", - defer = jQuery._data( elem, deferDataKey ); - if ( defer && - ( src === "queue" || !jQuery._data(elem, queueDataKey) ) && - ( src === "mark" || !jQuery._data(elem, markDataKey) ) ) { - // Give room for hard-coded callbacks to fire first - // and eventually mark/queue something else on the element - setTimeout( function() { - if ( !jQuery._data( elem, queueDataKey ) && - !jQuery._data( elem, markDataKey ) ) { - jQuery.removeData( elem, deferDataKey, true ); - defer.fire(); - } - }, 0 ); - } -} - -jQuery.extend({ - - _mark: function( elem, type ) { - if ( elem ) { - type = ( type || "fx" ) + "mark"; - jQuery._data( elem, type, (jQuery._data( elem, type ) || 0) + 1 ); - } - }, - - _unmark: function( force, elem, type ) { - if ( force !== true ) { - type = elem; - elem = force; - force = false; - } - if ( elem ) { - type = type || "fx"; - var key = type + "mark", - count = force ? 0 : ( (jQuery._data( elem, key ) || 1) - 1 ); - if ( count ) { - jQuery._data( elem, key, count ); - } else { - jQuery.removeData( elem, key, true ); - handleQueueMarkDefer( elem, type, "mark" ); - } - } - }, - - queue: function( elem, type, data ) { - var q; - if ( elem ) { - type = ( type || "fx" ) + "queue"; - q = jQuery._data( elem, type ); - - // Speed up dequeue by getting out quickly if this is just a lookup - if ( data ) { - if ( !q || jQuery.isArray(data) ) { - q = jQuery._data( elem, type, jQuery.makeArray(data) ); - } else { - q.push( data ); - } - } - return q || []; - } - }, - - dequeue: function( elem, type ) { - type = type || "fx"; - - var queue = jQuery.queue( elem, type ), - fn = queue.shift(), - hooks = {}; - - // If the fx queue is dequeued, always remove the progress sentinel - if ( fn === "inprogress" ) { - fn = queue.shift(); - } - - if ( fn ) { - // Add a progress sentinel to prevent the fx queue from being - // automatically dequeued - if ( type === "fx" ) { - queue.unshift( "inprogress" ); - } - - jQuery._data( elem, type + ".run", hooks ); - fn.call( elem, function() { - jQuery.dequeue( elem, type ); - }, hooks ); - } - - if ( !queue.length ) { - jQuery.removeData( elem, type + "queue " + type + ".run", true ); - handleQueueMarkDefer( elem, type, "queue" ); - } - } -}); - -jQuery.fn.extend({ - queue: function( type, data ) { - var setter = 2; - - if ( typeof type !== "string" ) { - data = type; - type = "fx"; - setter--; - } - - if ( arguments.length < setter ) { - return jQuery.queue( this[0], type ); - } - - return data === undefined ? - this : - this.each(function() { - var queue = jQuery.queue( this, type, data ); - - if ( type === "fx" && queue[0] !== "inprogress" ) { - jQuery.dequeue( this, type ); - } - }); - }, - dequeue: function( type ) { - return this.each(function() { - jQuery.dequeue( this, type ); - }); - }, - // Based off of the plugin by Clint Helfers, with permission. - // http://blindsignals.com/index.php/2009/07/jquery-delay/ - delay: function( time, type ) { - time = jQuery.fx ? jQuery.fx.speeds[ time ] || time : time; - type = type || "fx"; - - return this.queue( type, function( next, hooks ) { - var timeout = setTimeout( next, time ); - hooks.stop = function() { - clearTimeout( timeout ); - }; - }); - }, - clearQueue: function( type ) { - return this.queue( type || "fx", [] ); - }, - // Get a promise resolved when queues of a certain type - // are emptied (fx is the type by default) - promise: function( type, object ) { - if ( typeof type !== "string" ) { - object = type; - type = undefined; - } - type = type || "fx"; - var defer = jQuery.Deferred(), - elements = this, - i = elements.length, - count = 1, - deferDataKey = type + "defer", - queueDataKey = type + "queue", - markDataKey = type + "mark", - tmp; - function resolve() { - if ( !( --count ) ) { - defer.resolveWith( elements, [ elements ] ); - } - } - while( i-- ) { - if (( tmp = jQuery.data( elements[ i ], deferDataKey, undefined, true ) || - ( jQuery.data( elements[ i ], queueDataKey, undefined, true ) || - jQuery.data( elements[ i ], markDataKey, undefined, true ) ) && - jQuery.data( elements[ i ], deferDataKey, jQuery.Callbacks( "once memory" ), true ) )) { - count++; - tmp.add( resolve ); - } - } - resolve(); - return defer.promise( object ); - } -}); - - - - -var rclass = /[\n\t\r]/g, - rspace = /\s+/, - rreturn = /\r/g, - rtype = /^(?:button|input)$/i, - rfocusable = /^(?:button|input|object|select|textarea)$/i, - rclickable = /^a(?:rea)?$/i, - rboolean = /^(?:autofocus|autoplay|async|checked|controls|defer|disabled|hidden|loop|multiple|open|readonly|required|scoped|selected)$/i, - getSetAttribute = jQuery.support.getSetAttribute, - nodeHook, boolHook, fixSpecified; - -jQuery.fn.extend({ - attr: function( name, value ) { - return jQuery.access( this, jQuery.attr, name, value, arguments.length > 1 ); - }, - - removeAttr: function( name ) { - return this.each(function() { - jQuery.removeAttr( this, name ); - }); - }, - - prop: function( name, value ) { - return jQuery.access( this, jQuery.prop, name, value, arguments.length > 1 ); - }, - - removeProp: function( name ) { - name = jQuery.propFix[ name ] || name; - return this.each(function() { - // try/catch handles cases where IE balks (such as removing a property on window) - try { - this[ name ] = undefined; - delete this[ name ]; - } catch( e ) {} - }); - }, - - addClass: function( value ) { - var classNames, i, l, elem, - setClass, c, cl; - - if ( jQuery.isFunction( value ) ) { - return this.each(function( j ) { - jQuery( this ).addClass( value.call(this, j, this.className) ); - }); - } - - if ( value && typeof value === "string" ) { - classNames = value.split( rspace ); - - for ( i = 0, l = this.length; i < l; i++ ) { - elem = this[ i ]; - - if ( elem.nodeType === 1 ) { - if ( !elem.className && classNames.length === 1 ) { - elem.className = value; - - } else { - setClass = " " + elem.className + " "; - - for ( c = 0, cl = classNames.length; c < cl; c++ ) { - if ( !~setClass.indexOf( " " + classNames[ c ] + " " ) ) { - setClass += classNames[ c ] + " "; - } - } - elem.className = jQuery.trim( setClass ); - } - } - } - } - - return this; - }, - - removeClass: function( value ) { - var classNames, i, l, elem, className, c, cl; - - if ( jQuery.isFunction( value ) ) { - return this.each(function( j ) { - jQuery( this ).removeClass( value.call(this, j, this.className) ); - }); - } - - if ( (value && typeof value === "string") || value === undefined ) { - classNames = ( value || "" ).split( rspace ); - - for ( i = 0, l = this.length; i < l; i++ ) { - elem = this[ i ]; - - if ( elem.nodeType === 1 && elem.className ) { - if ( value ) { - className = (" " + elem.className + " ").replace( rclass, " " ); - for ( c = 0, cl = classNames.length; c < cl; c++ ) { - className = className.replace(" " + classNames[ c ] + " ", " "); - } - elem.className = jQuery.trim( className ); - - } else { - elem.className = ""; - } - } - } - } - - return this; - }, - - toggleClass: function( value, stateVal ) { - var type = typeof value, - isBool = typeof stateVal === "boolean"; - - if ( jQuery.isFunction( value ) ) { - return this.each(function( i ) { - jQuery( this ).toggleClass( value.call(this, i, this.className, stateVal), stateVal ); - }); - } - - return this.each(function() { - if ( type === "string" ) { - // toggle individual class names - var className, - i = 0, - self = jQuery( this ), - state = stateVal, - classNames = value.split( rspace ); - - while ( (className = classNames[ i++ ]) ) { - // check each className given, space separated list - state = isBool ? state : !self.hasClass( className ); - self[ state ? "addClass" : "removeClass" ]( className ); - } - - } else if ( type === "undefined" || type === "boolean" ) { - if ( this.className ) { - // store className if set - jQuery._data( this, "__className__", this.className ); - } - - // toggle whole className - this.className = this.className || value === false ? "" : jQuery._data( this, "__className__" ) || ""; - } - }); - }, - - hasClass: function( selector ) { - var className = " " + selector + " ", - i = 0, - l = this.length; - for ( ; i < l; i++ ) { - if ( this[i].nodeType === 1 && (" " + this[i].className + " ").replace(rclass, " ").indexOf( className ) > -1 ) { - return true; - } - } - - return false; - }, - - val: function( value ) { - var hooks, ret, isFunction, - elem = this[0]; - - if ( !arguments.length ) { - if ( elem ) { - hooks = jQuery.valHooks[ elem.type ] || jQuery.valHooks[ elem.nodeName.toLowerCase() ]; - - if ( hooks && "get" in hooks && (ret = hooks.get( elem, "value" )) !== undefined ) { - return ret; - } - - ret = elem.value; - - return typeof ret === "string" ? - // handle most common string cases - ret.replace(rreturn, "") : - // handle cases where value is null/undef or number - ret == null ? "" : ret; - } - - return; - } - - isFunction = jQuery.isFunction( value ); - - return this.each(function( i ) { - var self = jQuery(this), val; - - if ( this.nodeType !== 1 ) { - return; - } - - if ( isFunction ) { - val = value.call( this, i, self.val() ); - } else { - val = value; - } - - // Treat null/undefined as ""; convert numbers to string - if ( val == null ) { - val = ""; - } else if ( typeof val === "number" ) { - val += ""; - } else if ( jQuery.isArray( val ) ) { - val = jQuery.map(val, function ( value ) { - return value == null ? "" : value + ""; - }); - } - - hooks = jQuery.valHooks[ this.type ] || jQuery.valHooks[ this.nodeName.toLowerCase() ]; - - // If set returns undefined, fall back to normal setting - if ( !hooks || !("set" in hooks) || hooks.set( this, val, "value" ) === undefined ) { - this.value = val; - } - }); - } -}); - -jQuery.extend({ - valHooks: { - option: { - get: function( elem ) { - // attributes.value is undefined in Blackberry 4.7 but - // uses .value. See #6932 - var val = elem.attributes.value; - return !val || val.specified ? elem.value : elem.text; - } - }, - select: { - get: function( elem ) { - var value, i, max, option, - index = elem.selectedIndex, - values = [], - options = elem.options, - one = elem.type === "select-one"; - - // Nothing was selected - if ( index < 0 ) { - return null; - } - - // Loop through all the selected options - i = one ? index : 0; - max = one ? index + 1 : options.length; - for ( ; i < max; i++ ) { - option = options[ i ]; - - // Don't return options that are disabled or in a disabled optgroup - if ( option.selected && (jQuery.support.optDisabled ? !option.disabled : option.getAttribute("disabled") === null) && - (!option.parentNode.disabled || !jQuery.nodeName( option.parentNode, "optgroup" )) ) { - - // Get the specific value for the option - value = jQuery( option ).val(); - - // We don't need an array for one selects - if ( one ) { - return value; - } - - // Multi-Selects return an array - values.push( value ); - } - } - - // Fixes Bug #2551 -- select.val() broken in IE after form.reset() - if ( one && !values.length && options.length ) { - return jQuery( options[ index ] ).val(); - } - - return values; - }, - - set: function( elem, value ) { - var values = jQuery.makeArray( value ); - - jQuery(elem).find("option").each(function() { - this.selected = jQuery.inArray( jQuery(this).val(), values ) >= 0; - }); - - if ( !values.length ) { - elem.selectedIndex = -1; - } - return values; - } - } - }, - - attrFn: { - val: true, - css: true, - html: true, - text: true, - data: true, - width: true, - height: true, - offset: true - }, - - attr: function( elem, name, value, pass ) { - var ret, hooks, notxml, - nType = elem.nodeType; - - // don't get/set attributes on text, comment and attribute nodes - if ( !elem || nType === 3 || nType === 8 || nType === 2 ) { - return; - } - - if ( pass && name in jQuery.attrFn ) { - return jQuery( elem )[ name ]( value ); - } - - // Fallback to prop when attributes are not supported - if ( typeof elem.getAttribute === "undefined" ) { - return jQuery.prop( elem, name, value ); - } - - notxml = nType !== 1 || !jQuery.isXMLDoc( elem ); - - // All attributes are lowercase - // Grab necessary hook if one is defined - if ( notxml ) { - name = name.toLowerCase(); - hooks = jQuery.attrHooks[ name ] || ( rboolean.test( name ) ? boolHook : nodeHook ); - } - - if ( value !== undefined ) { - - if ( value === null ) { - jQuery.removeAttr( elem, name ); - return; - - } else if ( hooks && "set" in hooks && notxml && (ret = hooks.set( elem, value, name )) !== undefined ) { - return ret; - - } else { - elem.setAttribute( name, "" + value ); - return value; - } - - } else if ( hooks && "get" in hooks && notxml && (ret = hooks.get( elem, name )) !== null ) { - return ret; - - } else { - - ret = elem.getAttribute( name ); - - // Non-existent attributes return null, we normalize to undefined - return ret === null ? - undefined : - ret; - } - }, - - removeAttr: function( elem, value ) { - var propName, attrNames, name, l, isBool, - i = 0; - - if ( value && elem.nodeType === 1 ) { - attrNames = value.toLowerCase().split( rspace ); - l = attrNames.length; - - for ( ; i < l; i++ ) { - name = attrNames[ i ]; - - if ( name ) { - propName = jQuery.propFix[ name ] || name; - isBool = rboolean.test( name ); - - // See #9699 for explanation of this approach (setting first, then removal) - // Do not do this for boolean attributes (see #10870) - if ( !isBool ) { - jQuery.attr( elem, name, "" ); - } - elem.removeAttribute( getSetAttribute ? name : propName ); - - // Set corresponding property to false for boolean attributes - if ( isBool && propName in elem ) { - elem[ propName ] = false; - } - } - } - } - }, - - attrHooks: { - type: { - set: function( elem, value ) { - // We can't allow the type property to be changed (since it causes problems in IE) - if ( rtype.test( elem.nodeName ) && elem.parentNode ) { - jQuery.error( "type property can't be changed" ); - } else if ( !jQuery.support.radioValue && value === "radio" && jQuery.nodeName(elem, "input") ) { - // Setting the type on a radio button after the value resets the value in IE6-9 - // Reset value to it's default in case type is set after value - // This is for element creation - var val = elem.value; - elem.setAttribute( "type", value ); - if ( val ) { - elem.value = val; - } - return value; - } - } - }, - // Use the value property for back compat - // Use the nodeHook for button elements in IE6/7 (#1954) - value: { - get: function( elem, name ) { - if ( nodeHook && jQuery.nodeName( elem, "button" ) ) { - return nodeHook.get( elem, name ); - } - return name in elem ? - elem.value : - null; - }, - set: function( elem, value, name ) { - if ( nodeHook && jQuery.nodeName( elem, "button" ) ) { - return nodeHook.set( elem, value, name ); - } - // Does not return so that setAttribute is also used - elem.value = value; - } - } - }, - - propFix: { - tabindex: "tabIndex", - readonly: "readOnly", - "for": "htmlFor", - "class": "className", - maxlength: "maxLength", - cellspacing: "cellSpacing", - cellpadding: "cellPadding", - rowspan: "rowSpan", - colspan: "colSpan", - usemap: "useMap", - frameborder: "frameBorder", - contenteditable: "contentEditable" - }, - - prop: function( elem, name, value ) { - var ret, hooks, notxml, - nType = elem.nodeType; - - // don't get/set properties on text, comment and attribute nodes - if ( !elem || nType === 3 || nType === 8 || nType === 2 ) { - return; - } - - notxml = nType !== 1 || !jQuery.isXMLDoc( elem ); - - if ( notxml ) { - // Fix name and attach hooks - name = jQuery.propFix[ name ] || name; - hooks = jQuery.propHooks[ name ]; - } - - if ( value !== undefined ) { - if ( hooks && "set" in hooks && (ret = hooks.set( elem, value, name )) !== undefined ) { - return ret; - - } else { - return ( elem[ name ] = value ); - } - - } else { - if ( hooks && "get" in hooks && (ret = hooks.get( elem, name )) !== null ) { - return ret; - - } else { - return elem[ name ]; - } - } - }, - - propHooks: { - tabIndex: { - get: function( elem ) { - // elem.tabIndex doesn't always return the correct value when it hasn't been explicitly set - // http://fluidproject.org/blog/2008/01/09/getting-setting-and-removing-tabindex-values-with-javascript/ - var attributeNode = elem.getAttributeNode("tabindex"); - - return attributeNode && attributeNode.specified ? - parseInt( attributeNode.value, 10 ) : - rfocusable.test( elem.nodeName ) || rclickable.test( elem.nodeName ) && elem.href ? - 0 : - undefined; - } - } - } -}); - -// Add the tabIndex propHook to attrHooks for back-compat (different case is intentional) -jQuery.attrHooks.tabindex = jQuery.propHooks.tabIndex; - -// Hook for boolean attributes -boolHook = { - get: function( elem, name ) { - // Align boolean attributes with corresponding properties - // Fall back to attribute presence where some booleans are not supported - var attrNode, - property = jQuery.prop( elem, name ); - return property === true || typeof property !== "boolean" && ( attrNode = elem.getAttributeNode(name) ) && attrNode.nodeValue !== false ? - name.toLowerCase() : - undefined; - }, - set: function( elem, value, name ) { - var propName; - if ( value === false ) { - // Remove boolean attributes when set to false - jQuery.removeAttr( elem, name ); - } else { - // value is true since we know at this point it's type boolean and not false - // Set boolean attributes to the same name and set the DOM property - propName = jQuery.propFix[ name ] || name; - if ( propName in elem ) { - // Only set the IDL specifically if it already exists on the element - elem[ propName ] = true; - } - - elem.setAttribute( name, name.toLowerCase() ); - } - return name; - } -}; - -// IE6/7 do not support getting/setting some attributes with get/setAttribute -if ( !getSetAttribute ) { - - fixSpecified = { - name: true, - id: true, - coords: true - }; - - // Use this for any attribute in IE6/7 - // This fixes almost every IE6/7 issue - nodeHook = jQuery.valHooks.button = { - get: function( elem, name ) { - var ret; - ret = elem.getAttributeNode( name ); - return ret && ( fixSpecified[ name ] ? ret.nodeValue !== "" : ret.specified ) ? - ret.nodeValue : - undefined; - }, - set: function( elem, value, name ) { - // Set the existing or create a new attribute node - var ret = elem.getAttributeNode( name ); - if ( !ret ) { - ret = document.createAttribute( name ); - elem.setAttributeNode( ret ); - } - return ( ret.nodeValue = value + "" ); - } - }; - - // Apply the nodeHook to tabindex - jQuery.attrHooks.tabindex.set = nodeHook.set; - - // Set width and height to auto instead of 0 on empty string( Bug #8150 ) - // This is for removals - jQuery.each([ "width", "height" ], function( i, name ) { - jQuery.attrHooks[ name ] = jQuery.extend( jQuery.attrHooks[ name ], { - set: function( elem, value ) { - if ( value === "" ) { - elem.setAttribute( name, "auto" ); - return value; - } - } - }); - }); - - // Set contenteditable to false on removals(#10429) - // Setting to empty string throws an error as an invalid value - jQuery.attrHooks.contenteditable = { - get: nodeHook.get, - set: function( elem, value, name ) { - if ( value === "" ) { - value = "false"; - } - nodeHook.set( elem, value, name ); - } - }; -} - - -// Some attributes require a special call on IE -if ( !jQuery.support.hrefNormalized ) { - jQuery.each([ "href", "src", "width", "height" ], function( i, name ) { - jQuery.attrHooks[ name ] = jQuery.extend( jQuery.attrHooks[ name ], { - get: function( elem ) { - var ret = elem.getAttribute( name, 2 ); - return ret === null ? undefined : ret; - } - }); - }); -} - -if ( !jQuery.support.style ) { - jQuery.attrHooks.style = { - get: function( elem ) { - // Return undefined in the case of empty string - // Normalize to lowercase since IE uppercases css property names - return elem.style.cssText.toLowerCase() || undefined; - }, - set: function( elem, value ) { - return ( elem.style.cssText = "" + value ); - } - }; -} - -// Safari mis-reports the default selected property of an option -// Accessing the parent's selectedIndex property fixes it -if ( !jQuery.support.optSelected ) { - jQuery.propHooks.selected = jQuery.extend( jQuery.propHooks.selected, { - get: function( elem ) { - var parent = elem.parentNode; - - if ( parent ) { - parent.selectedIndex; - - // Make sure that it also works with optgroups, see #5701 - if ( parent.parentNode ) { - parent.parentNode.selectedIndex; - } - } - return null; - } - }); -} - -// IE6/7 call enctype encoding -if ( !jQuery.support.enctype ) { - jQuery.propFix.enctype = "encoding"; -} - -// Radios and checkboxes getter/setter -if ( !jQuery.support.checkOn ) { - jQuery.each([ "radio", "checkbox" ], function() { - jQuery.valHooks[ this ] = { - get: function( elem ) { - // Handle the case where in Webkit "" is returned instead of "on" if a value isn't specified - return elem.getAttribute("value") === null ? "on" : elem.value; - } - }; - }); -} -jQuery.each([ "radio", "checkbox" ], function() { - jQuery.valHooks[ this ] = jQuery.extend( jQuery.valHooks[ this ], { - set: function( elem, value ) { - if ( jQuery.isArray( value ) ) { - return ( elem.checked = jQuery.inArray( jQuery(elem).val(), value ) >= 0 ); - } - } - }); -}); - - - - -var rformElems = /^(?:textarea|input|select)$/i, - rtypenamespace = /^([^\.]*)?(?:\.(.+))?$/, - rhoverHack = /(?:^|\s)hover(\.\S+)?\b/, - rkeyEvent = /^key/, - rmouseEvent = /^(?:mouse|contextmenu)|click/, - rfocusMorph = /^(?:focusinfocus|focusoutblur)$/, - rquickIs = /^(\w*)(?:#([\w\-]+))?(?:\.([\w\-]+))?$/, - quickParse = function( selector ) { - var quick = rquickIs.exec( selector ); - if ( quick ) { - // 0 1 2 3 - // [ _, tag, id, class ] - quick[1] = ( quick[1] || "" ).toLowerCase(); - quick[3] = quick[3] && new RegExp( "(?:^|\\s)" + quick[3] + "(?:\\s|$)" ); - } - return quick; - }, - quickIs = function( elem, m ) { - var attrs = elem.attributes || {}; - return ( - (!m[1] || elem.nodeName.toLowerCase() === m[1]) && - (!m[2] || (attrs.id || {}).value === m[2]) && - (!m[3] || m[3].test( (attrs[ "class" ] || {}).value )) - ); - }, - hoverHack = function( events ) { - return jQuery.event.special.hover ? events : events.replace( rhoverHack, "mouseenter$1 mouseleave$1" ); - }; - -/* - * Helper functions for managing events -- not part of the public interface. - * Props to Dean Edwards' addEvent library for many of the ideas. - */ -jQuery.event = { - - add: function( elem, types, handler, data, selector ) { - - var elemData, eventHandle, events, - t, tns, type, namespaces, handleObj, - handleObjIn, quick, handlers, special; - - // Don't attach events to noData or text/comment nodes (allow plain objects tho) - if ( elem.nodeType === 3 || elem.nodeType === 8 || !types || !handler || !(elemData = jQuery._data( elem )) ) { - return; - } - - // Caller can pass in an object of custom data in lieu of the handler - if ( handler.handler ) { - handleObjIn = handler; - handler = handleObjIn.handler; - selector = handleObjIn.selector; - } - - // Make sure that the handler has a unique ID, used to find/remove it later - if ( !handler.guid ) { - handler.guid = jQuery.guid++; - } - - // Init the element's event structure and main handler, if this is the first - events = elemData.events; - if ( !events ) { - elemData.events = events = {}; - } - eventHandle = elemData.handle; - if ( !eventHandle ) { - elemData.handle = eventHandle = function( e ) { - // Discard the second event of a jQuery.event.trigger() and - // when an event is called after a page has unloaded - return typeof jQuery !== "undefined" && (!e || jQuery.event.triggered !== e.type) ? - jQuery.event.dispatch.apply( eventHandle.elem, arguments ) : - undefined; - }; - // Add elem as a property of the handle fn to prevent a memory leak with IE non-native events - eventHandle.elem = elem; - } - - // Handle multiple events separated by a space - // jQuery(...).bind("mouseover mouseout", fn); - types = jQuery.trim( hoverHack(types) ).split( " " ); - for ( t = 0; t < types.length; t++ ) { - - tns = rtypenamespace.exec( types[t] ) || []; - type = tns[1]; - namespaces = ( tns[2] || "" ).split( "." ).sort(); - - // If event changes its type, use the special event handlers for the changed type - special = jQuery.event.special[ type ] || {}; - - // If selector defined, determine special event api type, otherwise given type - type = ( selector ? special.delegateType : special.bindType ) || type; - - // Update special based on newly reset type - special = jQuery.event.special[ type ] || {}; - - // handleObj is passed to all event handlers - handleObj = jQuery.extend({ - type: type, - origType: tns[1], - data: data, - handler: handler, - guid: handler.guid, - selector: selector, - quick: selector && quickParse( selector ), - namespace: namespaces.join(".") - }, handleObjIn ); - - // Init the event handler queue if we're the first - handlers = events[ type ]; - if ( !handlers ) { - handlers = events[ type ] = []; - handlers.delegateCount = 0; - - // Only use addEventListener/attachEvent if the special events handler returns false - if ( !special.setup || special.setup.call( elem, data, namespaces, eventHandle ) === false ) { - // Bind the global event handler to the element - if ( elem.addEventListener ) { - elem.addEventListener( type, eventHandle, false ); - - } else if ( elem.attachEvent ) { - elem.attachEvent( "on" + type, eventHandle ); - } - } - } - - if ( special.add ) { - special.add.call( elem, handleObj ); - - if ( !handleObj.handler.guid ) { - handleObj.handler.guid = handler.guid; - } - } - - // Add to the element's handler list, delegates in front - if ( selector ) { - handlers.splice( handlers.delegateCount++, 0, handleObj ); - } else { - handlers.push( handleObj ); - } - - // Keep track of which events have ever been used, for event optimization - jQuery.event.global[ type ] = true; - } - - // Nullify elem to prevent memory leaks in IE - elem = null; - }, - - global: {}, - - // Detach an event or set of events from an element - remove: function( elem, types, handler, selector, mappedTypes ) { - - var elemData = jQuery.hasData( elem ) && jQuery._data( elem ), - t, tns, type, origType, namespaces, origCount, - j, events, special, handle, eventType, handleObj; - - if ( !elemData || !(events = elemData.events) ) { - return; - } - - // Once for each type.namespace in types; type may be omitted - types = jQuery.trim( hoverHack( types || "" ) ).split(" "); - for ( t = 0; t < types.length; t++ ) { - tns = rtypenamespace.exec( types[t] ) || []; - type = origType = tns[1]; - namespaces = tns[2]; - - // Unbind all events (on this namespace, if provided) for the element - if ( !type ) { - for ( type in events ) { - jQuery.event.remove( elem, type + types[ t ], handler, selector, true ); - } - continue; - } - - special = jQuery.event.special[ type ] || {}; - type = ( selector? special.delegateType : special.bindType ) || type; - eventType = events[ type ] || []; - origCount = eventType.length; - namespaces = namespaces ? new RegExp("(^|\\.)" + namespaces.split(".").sort().join("\\.(?:.*\\.)?") + "(\\.|$)") : null; - - // Remove matching events - for ( j = 0; j < eventType.length; j++ ) { - handleObj = eventType[ j ]; - - if ( ( mappedTypes || origType === handleObj.origType ) && - ( !handler || handler.guid === handleObj.guid ) && - ( !namespaces || namespaces.test( handleObj.namespace ) ) && - ( !selector || selector === handleObj.selector || selector === "**" && handleObj.selector ) ) { - eventType.splice( j--, 1 ); - - if ( handleObj.selector ) { - eventType.delegateCount--; - } - if ( special.remove ) { - special.remove.call( elem, handleObj ); - } - } - } - - // Remove generic event handler if we removed something and no more handlers exist - // (avoids potential for endless recursion during removal of special event handlers) - if ( eventType.length === 0 && origCount !== eventType.length ) { - if ( !special.teardown || special.teardown.call( elem, namespaces ) === false ) { - jQuery.removeEvent( elem, type, elemData.handle ); - } - - delete events[ type ]; - } - } - - // Remove the expando if it's no longer used - if ( jQuery.isEmptyObject( events ) ) { - handle = elemData.handle; - if ( handle ) { - handle.elem = null; - } - - // removeData also checks for emptiness and clears the expando if empty - // so use it instead of delete - jQuery.removeData( elem, [ "events", "handle" ], true ); - } - }, - - // Events that are safe to short-circuit if no handlers are attached. - // Native DOM events should not be added, they may have inline handlers. - customEvent: { - "getData": true, - "setData": true, - "changeData": true - }, - - trigger: function( event, data, elem, onlyHandlers ) { - // Don't do events on text and comment nodes - if ( elem && (elem.nodeType === 3 || elem.nodeType === 8) ) { - return; - } - - // Event object or event type - var type = event.type || event, - namespaces = [], - cache, exclusive, i, cur, old, ontype, special, handle, eventPath, bubbleType; - - // focus/blur morphs to focusin/out; ensure we're not firing them right now - if ( rfocusMorph.test( type + jQuery.event.triggered ) ) { - return; - } - - if ( type.indexOf( "!" ) >= 0 ) { - // Exclusive events trigger only for the exact event (no namespaces) - type = type.slice(0, -1); - exclusive = true; - } - - if ( type.indexOf( "." ) >= 0 ) { - // Namespaced trigger; create a regexp to match event type in handle() - namespaces = type.split("."); - type = namespaces.shift(); - namespaces.sort(); - } - - if ( (!elem || jQuery.event.customEvent[ type ]) && !jQuery.event.global[ type ] ) { - // No jQuery handlers for this event type, and it can't have inline handlers - return; - } - - // Caller can pass in an Event, Object, or just an event type string - event = typeof event === "object" ? - // jQuery.Event object - event[ jQuery.expando ] ? event : - // Object literal - new jQuery.Event( type, event ) : - // Just the event type (string) - new jQuery.Event( type ); - - event.type = type; - event.isTrigger = true; - event.exclusive = exclusive; - event.namespace = namespaces.join( "." ); - event.namespace_re = event.namespace? new RegExp("(^|\\.)" + namespaces.join("\\.(?:.*\\.)?") + "(\\.|$)") : null; - ontype = type.indexOf( ":" ) < 0 ? "on" + type : ""; - - // Handle a global trigger - if ( !elem ) { - - // TODO: Stop taunting the data cache; remove global events and always attach to document - cache = jQuery.cache; - for ( i in cache ) { - if ( cache[ i ].events && cache[ i ].events[ type ] ) { - jQuery.event.trigger( event, data, cache[ i ].handle.elem, true ); - } - } - return; - } - - // Clean up the event in case it is being reused - event.result = undefined; - if ( !event.target ) { - event.target = elem; - } - - // Clone any incoming data and prepend the event, creating the handler arg list - data = data != null ? jQuery.makeArray( data ) : []; - data.unshift( event ); - - // Allow special events to draw outside the lines - special = jQuery.event.special[ type ] || {}; - if ( special.trigger && special.trigger.apply( elem, data ) === false ) { - return; - } - - // Determine event propagation path in advance, per W3C events spec (#9951) - // Bubble up to document, then to window; watch for a global ownerDocument var (#9724) - eventPath = [[ elem, special.bindType || type ]]; - if ( !onlyHandlers && !special.noBubble && !jQuery.isWindow( elem ) ) { - - bubbleType = special.delegateType || type; - cur = rfocusMorph.test( bubbleType + type ) ? elem : elem.parentNode; - old = null; - for ( ; cur; cur = cur.parentNode ) { - eventPath.push([ cur, bubbleType ]); - old = cur; - } - - // Only add window if we got to document (e.g., not plain obj or detached DOM) - if ( old && old === elem.ownerDocument ) { - eventPath.push([ old.defaultView || old.parentWindow || window, bubbleType ]); - } - } - - // Fire handlers on the event path - for ( i = 0; i < eventPath.length && !event.isPropagationStopped(); i++ ) { - - cur = eventPath[i][0]; - event.type = eventPath[i][1]; - - handle = ( jQuery._data( cur, "events" ) || {} )[ event.type ] && jQuery._data( cur, "handle" ); - if ( handle ) { - handle.apply( cur, data ); - } - // Note that this is a bare JS function and not a jQuery handler - handle = ontype && cur[ ontype ]; - if ( handle && jQuery.acceptData( cur ) && handle.apply( cur, data ) === false ) { - event.preventDefault(); - } - } - event.type = type; - - // If nobody prevented the default action, do it now - if ( !onlyHandlers && !event.isDefaultPrevented() ) { - - if ( (!special._default || special._default.apply( elem.ownerDocument, data ) === false) && - !(type === "click" && jQuery.nodeName( elem, "a" )) && jQuery.acceptData( elem ) ) { - - // Call a native DOM method on the target with the same name name as the event. - // Can't use an .isFunction() check here because IE6/7 fails that test. - // Don't do default actions on window, that's where global variables be (#6170) - // IE<9 dies on focus/blur to hidden element (#1486) - if ( ontype && elem[ type ] && ((type !== "focus" && type !== "blur") || event.target.offsetWidth !== 0) && !jQuery.isWindow( elem ) ) { - - // Don't re-trigger an onFOO event when we call its FOO() method - old = elem[ ontype ]; - - if ( old ) { - elem[ ontype ] = null; - } - - // Prevent re-triggering of the same event, since we already bubbled it above - jQuery.event.triggered = type; - elem[ type ](); - jQuery.event.triggered = undefined; - - if ( old ) { - elem[ ontype ] = old; - } - } - } - } - - return event.result; - }, - - dispatch: function( event ) { - - // Make a writable jQuery.Event from the native event object - event = jQuery.event.fix( event || window.event ); - - var handlers = ( (jQuery._data( this, "events" ) || {} )[ event.type ] || []), - delegateCount = handlers.delegateCount, - args = [].slice.call( arguments, 0 ), - run_all = !event.exclusive && !event.namespace, - special = jQuery.event.special[ event.type ] || {}, - handlerQueue = [], - i, j, cur, jqcur, ret, selMatch, matched, matches, handleObj, sel, related; - - // Use the fix-ed jQuery.Event rather than the (read-only) native event - args[0] = event; - event.delegateTarget = this; - - // Call the preDispatch hook for the mapped type, and let it bail if desired - if ( special.preDispatch && special.preDispatch.call( this, event ) === false ) { - return; - } - - // Determine handlers that should run if there are delegated events - // Avoid non-left-click bubbling in Firefox (#3861) - if ( delegateCount && !(event.button && event.type === "click") ) { - - // Pregenerate a single jQuery object for reuse with .is() - jqcur = jQuery(this); - jqcur.context = this.ownerDocument || this; - - for ( cur = event.target; cur != this; cur = cur.parentNode || this ) { - - // Don't process events on disabled elements (#6911, #8165) - if ( cur.disabled !== true ) { - selMatch = {}; - matches = []; - jqcur[0] = cur; - for ( i = 0; i < delegateCount; i++ ) { - handleObj = handlers[ i ]; - sel = handleObj.selector; - - if ( selMatch[ sel ] === undefined ) { - selMatch[ sel ] = ( - handleObj.quick ? quickIs( cur, handleObj.quick ) : jqcur.is( sel ) - ); - } - if ( selMatch[ sel ] ) { - matches.push( handleObj ); - } - } - if ( matches.length ) { - handlerQueue.push({ elem: cur, matches: matches }); - } - } - } - } - - // Add the remaining (directly-bound) handlers - if ( handlers.length > delegateCount ) { - handlerQueue.push({ elem: this, matches: handlers.slice( delegateCount ) }); - } - - // Run delegates first; they may want to stop propagation beneath us - for ( i = 0; i < handlerQueue.length && !event.isPropagationStopped(); i++ ) { - matched = handlerQueue[ i ]; - event.currentTarget = matched.elem; - - for ( j = 0; j < matched.matches.length && !event.isImmediatePropagationStopped(); j++ ) { - handleObj = matched.matches[ j ]; - - // Triggered event must either 1) be non-exclusive and have no namespace, or - // 2) have namespace(s) a subset or equal to those in the bound event (both can have no namespace). - if ( run_all || (!event.namespace && !handleObj.namespace) || event.namespace_re && event.namespace_re.test( handleObj.namespace ) ) { - - event.data = handleObj.data; - event.handleObj = handleObj; - - ret = ( (jQuery.event.special[ handleObj.origType ] || {}).handle || handleObj.handler ) - .apply( matched.elem, args ); - - if ( ret !== undefined ) { - event.result = ret; - if ( ret === false ) { - event.preventDefault(); - event.stopPropagation(); - } - } - } - } - } - - // Call the postDispatch hook for the mapped type - if ( special.postDispatch ) { - special.postDispatch.call( this, event ); - } - - return event.result; - }, - - // Includes some event props shared by KeyEvent and MouseEvent - // *** attrChange attrName relatedNode srcElement are not normalized, non-W3C, deprecated, will be removed in 1.8 *** - props: "attrChange attrName relatedNode srcElement altKey bubbles cancelable ctrlKey currentTarget eventPhase metaKey relatedTarget shiftKey target timeStamp view which".split(" "), - - fixHooks: {}, - - keyHooks: { - props: "char charCode key keyCode".split(" "), - filter: function( event, original ) { - - // Add which for key events - if ( event.which == null ) { - event.which = original.charCode != null ? original.charCode : original.keyCode; - } - - return event; - } - }, - - mouseHooks: { - props: "button buttons clientX clientY fromElement offsetX offsetY pageX pageY screenX screenY toElement".split(" "), - filter: function( event, original ) { - var eventDoc, doc, body, - button = original.button, - fromElement = original.fromElement; - - // Calculate pageX/Y if missing and clientX/Y available - if ( event.pageX == null && original.clientX != null ) { - eventDoc = event.target.ownerDocument || document; - doc = eventDoc.documentElement; - body = eventDoc.body; - - event.pageX = original.clientX + ( doc && doc.scrollLeft || body && body.scrollLeft || 0 ) - ( doc && doc.clientLeft || body && body.clientLeft || 0 ); - event.pageY = original.clientY + ( doc && doc.scrollTop || body && body.scrollTop || 0 ) - ( doc && doc.clientTop || body && body.clientTop || 0 ); - } - - // Add relatedTarget, if necessary - if ( !event.relatedTarget && fromElement ) { - event.relatedTarget = fromElement === event.target ? original.toElement : fromElement; - } - - // Add which for click: 1 === left; 2 === middle; 3 === right - // Note: button is not normalized, so don't use it - if ( !event.which && button !== undefined ) { - event.which = ( button & 1 ? 1 : ( button & 2 ? 3 : ( button & 4 ? 2 : 0 ) ) ); - } - - return event; - } - }, - - fix: function( event ) { - if ( event[ jQuery.expando ] ) { - return event; - } - - // Create a writable copy of the event object and normalize some properties - var i, prop, - originalEvent = event, - fixHook = jQuery.event.fixHooks[ event.type ] || {}, - copy = fixHook.props ? this.props.concat( fixHook.props ) : this.props; - - event = jQuery.Event( originalEvent ); - - for ( i = copy.length; i; ) { - prop = copy[ --i ]; - event[ prop ] = originalEvent[ prop ]; - } - - // Fix target property, if necessary (#1925, IE 6/7/8 & Safari2) - if ( !event.target ) { - event.target = originalEvent.srcElement || document; - } - - // Target should not be a text node (#504, Safari) - if ( event.target.nodeType === 3 ) { - event.target = event.target.parentNode; - } - - // For mouse/key events; add metaKey if it's not there (#3368, IE6/7/8) - if ( event.metaKey === undefined ) { - event.metaKey = event.ctrlKey; - } - - return fixHook.filter? fixHook.filter( event, originalEvent ) : event; - }, - - special: { - ready: { - // Make sure the ready event is setup - setup: jQuery.bindReady - }, - - load: { - // Prevent triggered image.load events from bubbling to window.load - noBubble: true - }, - - focus: { - delegateType: "focusin" - }, - blur: { - delegateType: "focusout" - }, - - beforeunload: { - setup: function( data, namespaces, eventHandle ) { - // We only want to do this special case on windows - if ( jQuery.isWindow( this ) ) { - this.onbeforeunload = eventHandle; - } - }, - - teardown: function( namespaces, eventHandle ) { - if ( this.onbeforeunload === eventHandle ) { - this.onbeforeunload = null; - } - } - } - }, - - simulate: function( type, elem, event, bubble ) { - // Piggyback on a donor event to simulate a different one. - // Fake originalEvent to avoid donor's stopPropagation, but if the - // simulated event prevents default then we do the same on the donor. - var e = jQuery.extend( - new jQuery.Event(), - event, - { type: type, - isSimulated: true, - originalEvent: {} - } - ); - if ( bubble ) { - jQuery.event.trigger( e, null, elem ); - } else { - jQuery.event.dispatch.call( elem, e ); - } - if ( e.isDefaultPrevented() ) { - event.preventDefault(); - } - } -}; - -// Some plugins are using, but it's undocumented/deprecated and will be removed. -// The 1.7 special event interface should provide all the hooks needed now. -jQuery.event.handle = jQuery.event.dispatch; - -jQuery.removeEvent = document.removeEventListener ? - function( elem, type, handle ) { - if ( elem.removeEventListener ) { - elem.removeEventListener( type, handle, false ); - } - } : - function( elem, type, handle ) { - if ( elem.detachEvent ) { - elem.detachEvent( "on" + type, handle ); - } - }; - -jQuery.Event = function( src, props ) { - // Allow instantiation without the 'new' keyword - if ( !(this instanceof jQuery.Event) ) { - return new jQuery.Event( src, props ); - } - - // Event object - if ( src && src.type ) { - this.originalEvent = src; - this.type = src.type; - - // Events bubbling up the document may have been marked as prevented - // by a handler lower down the tree; reflect the correct value. - this.isDefaultPrevented = ( src.defaultPrevented || src.returnValue === false || - src.getPreventDefault && src.getPreventDefault() ) ? returnTrue : returnFalse; - - // Event type - } else { - this.type = src; - } - - // Put explicitly provided properties onto the event object - if ( props ) { - jQuery.extend( this, props ); - } - - // Create a timestamp if incoming event doesn't have one - this.timeStamp = src && src.timeStamp || jQuery.now(); - - // Mark it as fixed - this[ jQuery.expando ] = true; -}; - -function returnFalse() { - return false; -} -function returnTrue() { - return true; -} - -// jQuery.Event is based on DOM3 Events as specified by the ECMAScript Language Binding -// http://www.w3.org/TR/2003/WD-DOM-Level-3-Events-20030331/ecma-script-binding.html -jQuery.Event.prototype = { - preventDefault: function() { - this.isDefaultPrevented = returnTrue; - - var e = this.originalEvent; - if ( !e ) { - return; - } - - // if preventDefault exists run it on the original event - if ( e.preventDefault ) { - e.preventDefault(); - - // otherwise set the returnValue property of the original event to false (IE) - } else { - e.returnValue = false; - } - }, - stopPropagation: function() { - this.isPropagationStopped = returnTrue; - - var e = this.originalEvent; - if ( !e ) { - return; - } - // if stopPropagation exists run it on the original event - if ( e.stopPropagation ) { - e.stopPropagation(); - } - // otherwise set the cancelBubble property of the original event to true (IE) - e.cancelBubble = true; - }, - stopImmediatePropagation: function() { - this.isImmediatePropagationStopped = returnTrue; - this.stopPropagation(); - }, - isDefaultPrevented: returnFalse, - isPropagationStopped: returnFalse, - isImmediatePropagationStopped: returnFalse -}; - -// Create mouseenter/leave events using mouseover/out and event-time checks -jQuery.each({ - mouseenter: "mouseover", - mouseleave: "mouseout" -}, function( orig, fix ) { - jQuery.event.special[ orig ] = { - delegateType: fix, - bindType: fix, - - handle: function( event ) { - var target = this, - related = event.relatedTarget, - handleObj = event.handleObj, - selector = handleObj.selector, - ret; - - // For mousenter/leave call the handler if related is outside the target. - // NB: No relatedTarget if the mouse left/entered the browser window - if ( !related || (related !== target && !jQuery.contains( target, related )) ) { - event.type = handleObj.origType; - ret = handleObj.handler.apply( this, arguments ); - event.type = fix; - } - return ret; - } - }; -}); - -// IE submit delegation -if ( !jQuery.support.submitBubbles ) { - - jQuery.event.special.submit = { - setup: function() { - // Only need this for delegated form submit events - if ( jQuery.nodeName( this, "form" ) ) { - return false; - } - - // Lazy-add a submit handler when a descendant form may potentially be submitted - jQuery.event.add( this, "click._submit keypress._submit", function( e ) { - // Node name check avoids a VML-related crash in IE (#9807) - var elem = e.target, - form = jQuery.nodeName( elem, "input" ) || jQuery.nodeName( elem, "button" ) ? elem.form : undefined; - if ( form && !form._submit_attached ) { - jQuery.event.add( form, "submit._submit", function( event ) { - event._submit_bubble = true; - }); - form._submit_attached = true; - } - }); - // return undefined since we don't need an event listener - }, - - postDispatch: function( event ) { - // If form was submitted by the user, bubble the event up the tree - if ( event._submit_bubble ) { - delete event._submit_bubble; - if ( this.parentNode && !event.isTrigger ) { - jQuery.event.simulate( "submit", this.parentNode, event, true ); - } - } - }, - - teardown: function() { - // Only need this for delegated form submit events - if ( jQuery.nodeName( this, "form" ) ) { - return false; - } - - // Remove delegated handlers; cleanData eventually reaps submit handlers attached above - jQuery.event.remove( this, "._submit" ); - } - }; -} - -// IE change delegation and checkbox/radio fix -if ( !jQuery.support.changeBubbles ) { - - jQuery.event.special.change = { - - setup: function() { - - if ( rformElems.test( this.nodeName ) ) { - // IE doesn't fire change on a check/radio until blur; trigger it on click - // after a propertychange. Eat the blur-change in special.change.handle. - // This still fires onchange a second time for check/radio after blur. - if ( this.type === "checkbox" || this.type === "radio" ) { - jQuery.event.add( this, "propertychange._change", function( event ) { - if ( event.originalEvent.propertyName === "checked" ) { - this._just_changed = true; - } - }); - jQuery.event.add( this, "click._change", function( event ) { - if ( this._just_changed && !event.isTrigger ) { - this._just_changed = false; - jQuery.event.simulate( "change", this, event, true ); - } - }); - } - return false; - } - // Delegated event; lazy-add a change handler on descendant inputs - jQuery.event.add( this, "beforeactivate._change", function( e ) { - var elem = e.target; - - if ( rformElems.test( elem.nodeName ) && !elem._change_attached ) { - jQuery.event.add( elem, "change._change", function( event ) { - if ( this.parentNode && !event.isSimulated && !event.isTrigger ) { - jQuery.event.simulate( "change", this.parentNode, event, true ); - } - }); - elem._change_attached = true; - } - }); - }, - - handle: function( event ) { - var elem = event.target; - - // Swallow native change events from checkbox/radio, we already triggered them above - if ( this !== elem || event.isSimulated || event.isTrigger || (elem.type !== "radio" && elem.type !== "checkbox") ) { - return event.handleObj.handler.apply( this, arguments ); - } - }, - - teardown: function() { - jQuery.event.remove( this, "._change" ); - - return rformElems.test( this.nodeName ); - } - }; -} - -// Create "bubbling" focus and blur events -if ( !jQuery.support.focusinBubbles ) { - jQuery.each({ focus: "focusin", blur: "focusout" }, function( orig, fix ) { - - // Attach a single capturing handler while someone wants focusin/focusout - var attaches = 0, - handler = function( event ) { - jQuery.event.simulate( fix, event.target, jQuery.event.fix( event ), true ); - }; - - jQuery.event.special[ fix ] = { - setup: function() { - if ( attaches++ === 0 ) { - document.addEventListener( orig, handler, true ); - } - }, - teardown: function() { - if ( --attaches === 0 ) { - document.removeEventListener( orig, handler, true ); - } - } - }; - }); -} - -jQuery.fn.extend({ - - on: function( types, selector, data, fn, /*INTERNAL*/ one ) { - var origFn, type; - - // Types can be a map of types/handlers - if ( typeof types === "object" ) { - // ( types-Object, selector, data ) - if ( typeof selector !== "string" ) { // && selector != null - // ( types-Object, data ) - data = data || selector; - selector = undefined; - } - for ( type in types ) { - this.on( type, selector, data, types[ type ], one ); - } - return this; - } - - if ( data == null && fn == null ) { - // ( types, fn ) - fn = selector; - data = selector = undefined; - } else if ( fn == null ) { - if ( typeof selector === "string" ) { - // ( types, selector, fn ) - fn = data; - data = undefined; - } else { - // ( types, data, fn ) - fn = data; - data = selector; - selector = undefined; - } - } - if ( fn === false ) { - fn = returnFalse; - } else if ( !fn ) { - return this; - } - - if ( one === 1 ) { - origFn = fn; - fn = function( event ) { - // Can use an empty set, since event contains the info - jQuery().off( event ); - return origFn.apply( this, arguments ); - }; - // Use same guid so caller can remove using origFn - fn.guid = origFn.guid || ( origFn.guid = jQuery.guid++ ); - } - return this.each( function() { - jQuery.event.add( this, types, fn, data, selector ); - }); - }, - one: function( types, selector, data, fn ) { - return this.on( types, selector, data, fn, 1 ); - }, - off: function( types, selector, fn ) { - if ( types && types.preventDefault && types.handleObj ) { - // ( event ) dispatched jQuery.Event - var handleObj = types.handleObj; - jQuery( types.delegateTarget ).off( - handleObj.namespace ? handleObj.origType + "." + handleObj.namespace : handleObj.origType, - handleObj.selector, - handleObj.handler - ); - return this; - } - if ( typeof types === "object" ) { - // ( types-object [, selector] ) - for ( var type in types ) { - this.off( type, selector, types[ type ] ); - } - return this; - } - if ( selector === false || typeof selector === "function" ) { - // ( types [, fn] ) - fn = selector; - selector = undefined; - } - if ( fn === false ) { - fn = returnFalse; - } - return this.each(function() { - jQuery.event.remove( this, types, fn, selector ); - }); - }, - - bind: function( types, data, fn ) { - return this.on( types, null, data, fn ); - }, - unbind: function( types, fn ) { - return this.off( types, null, fn ); - }, - - live: function( types, data, fn ) { - jQuery( this.context ).on( types, this.selector, data, fn ); - return this; - }, - die: function( types, fn ) { - jQuery( this.context ).off( types, this.selector || "**", fn ); - return this; - }, - - delegate: function( selector, types, data, fn ) { - return this.on( types, selector, data, fn ); - }, - undelegate: function( selector, types, fn ) { - // ( namespace ) or ( selector, types [, fn] ) - return arguments.length == 1? this.off( selector, "**" ) : this.off( types, selector, fn ); - }, - - trigger: function( type, data ) { - return this.each(function() { - jQuery.event.trigger( type, data, this ); - }); - }, - triggerHandler: function( type, data ) { - if ( this[0] ) { - return jQuery.event.trigger( type, data, this[0], true ); - } - }, - - toggle: function( fn ) { - // Save reference to arguments for access in closure - var args = arguments, - guid = fn.guid || jQuery.guid++, - i = 0, - toggler = function( event ) { - // Figure out which function to execute - var lastToggle = ( jQuery._data( this, "lastToggle" + fn.guid ) || 0 ) % i; - jQuery._data( this, "lastToggle" + fn.guid, lastToggle + 1 ); - - // Make sure that clicks stop - event.preventDefault(); - - // and execute the function - return args[ lastToggle ].apply( this, arguments ) || false; - }; - - // link all the functions, so any of them can unbind this click handler - toggler.guid = guid; - while ( i < args.length ) { - args[ i++ ].guid = guid; - } - - return this.click( toggler ); - }, - - hover: function( fnOver, fnOut ) { - return this.mouseenter( fnOver ).mouseleave( fnOut || fnOver ); - } -}); - -jQuery.each( ("blur focus focusin focusout load resize scroll unload click dblclick " + - "mousedown mouseup mousemove mouseover mouseout mouseenter mouseleave " + - "change select submit keydown keypress keyup error contextmenu").split(" "), function( i, name ) { - - // Handle event binding - jQuery.fn[ name ] = function( data, fn ) { - if ( fn == null ) { - fn = data; - data = null; - } - - return arguments.length > 0 ? - this.on( name, null, data, fn ) : - this.trigger( name ); - }; - - if ( jQuery.attrFn ) { - jQuery.attrFn[ name ] = true; - } - - if ( rkeyEvent.test( name ) ) { - jQuery.event.fixHooks[ name ] = jQuery.event.keyHooks; - } - - if ( rmouseEvent.test( name ) ) { - jQuery.event.fixHooks[ name ] = jQuery.event.mouseHooks; - } -}); - - - -/*! - * Sizzle CSS Selector Engine - * Copyright 2011, The Dojo Foundation - * Released under the MIT, BSD, and GPL Licenses. - * More information: http://sizzlejs.com/ - */ -(function(){ - -var chunker = /((?:\((?:\([^()]+\)|[^()]+)+\)|\[(?:\[[^\[\]]*\]|['"][^'"]*['"]|[^\[\]'"]+)+\]|\\.|[^ >+~,(\[\\]+)+|[>+~])(\s*,\s*)?((?:.|\r|\n)*)/g, - expando = "sizcache" + (Math.random() + '').replace('.', ''), - done = 0, - toString = Object.prototype.toString, - hasDuplicate = false, - baseHasDuplicate = true, - rBackslash = /\\/g, - rReturn = /\r\n/g, - rNonWord = /\W/; - -// Here we check if the JavaScript engine is using some sort of -// optimization where it does not always call our comparision -// function. If that is the case, discard the hasDuplicate value. -// Thus far that includes Google Chrome. -[0, 0].sort(function() { - baseHasDuplicate = false; - return 0; -}); - -var Sizzle = function( selector, context, results, seed ) { - results = results || []; - context = context || document; - - var origContext = context; - - if ( context.nodeType !== 1 && context.nodeType !== 9 ) { - return []; - } - - if ( !selector || typeof selector !== "string" ) { - return results; - } - - var m, set, checkSet, extra, ret, cur, pop, i, - prune = true, - contextXML = Sizzle.isXML( context ), - parts = [], - soFar = selector; - - // Reset the position of the chunker regexp (start from head) - do { - chunker.exec( "" ); - m = chunker.exec( soFar ); - - if ( m ) { - soFar = m[3]; - - parts.push( m[1] ); - - if ( m[2] ) { - extra = m[3]; - break; - } - } - } while ( m ); - - if ( parts.length > 1 && origPOS.exec( selector ) ) { - - if ( parts.length === 2 && Expr.relative[ parts[0] ] ) { - set = posProcess( parts[0] + parts[1], context, seed ); - - } else { - set = Expr.relative[ parts[0] ] ? - [ context ] : - Sizzle( parts.shift(), context ); - - while ( parts.length ) { - selector = parts.shift(); - - if ( Expr.relative[ selector ] ) { - selector += parts.shift(); - } - - set = posProcess( selector, set, seed ); - } - } - - } else { - // Take a shortcut and set the context if the root selector is an ID - // (but not if it'll be faster if the inner selector is an ID) - if ( !seed && parts.length > 1 && context.nodeType === 9 && !contextXML && - Expr.match.ID.test(parts[0]) && !Expr.match.ID.test(parts[parts.length - 1]) ) { - - ret = Sizzle.find( parts.shift(), context, contextXML ); - context = ret.expr ? - Sizzle.filter( ret.expr, ret.set )[0] : - ret.set[0]; - } - - if ( context ) { - ret = seed ? - { expr: parts.pop(), set: makeArray(seed) } : - Sizzle.find( parts.pop(), parts.length === 1 && (parts[0] === "~" || parts[0] === "+") && context.parentNode ? context.parentNode : context, contextXML ); - - set = ret.expr ? - Sizzle.filter( ret.expr, ret.set ) : - ret.set; - - if ( parts.length > 0 ) { - checkSet = makeArray( set ); - - } else { - prune = false; - } - - while ( parts.length ) { - cur = parts.pop(); - pop = cur; - - if ( !Expr.relative[ cur ] ) { - cur = ""; - } else { - pop = parts.pop(); - } - - if ( pop == null ) { - pop = context; - } - - Expr.relative[ cur ]( checkSet, pop, contextXML ); - } - - } else { - checkSet = parts = []; - } - } - - if ( !checkSet ) { - checkSet = set; - } - - if ( !checkSet ) { - Sizzle.error( cur || selector ); - } - - if ( toString.call(checkSet) === "[object Array]" ) { - if ( !prune ) { - results.push.apply( results, checkSet ); - - } else if ( context && context.nodeType === 1 ) { - for ( i = 0; checkSet[i] != null; i++ ) { - if ( checkSet[i] && (checkSet[i] === true || checkSet[i].nodeType === 1 && Sizzle.contains(context, checkSet[i])) ) { - results.push( set[i] ); - } - } - - } else { - for ( i = 0; checkSet[i] != null; i++ ) { - if ( checkSet[i] && checkSet[i].nodeType === 1 ) { - results.push( set[i] ); - } - } - } - - } else { - makeArray( checkSet, results ); - } - - if ( extra ) { - Sizzle( extra, origContext, results, seed ); - Sizzle.uniqueSort( results ); - } - - return results; -}; - -Sizzle.uniqueSort = function( results ) { - if ( sortOrder ) { - hasDuplicate = baseHasDuplicate; - results.sort( sortOrder ); - - if ( hasDuplicate ) { - for ( var i = 1; i < results.length; i++ ) { - if ( results[i] === results[ i - 1 ] ) { - results.splice( i--, 1 ); - } - } - } - } - - return results; -}; - -Sizzle.matches = function( expr, set ) { - return Sizzle( expr, null, null, set ); -}; - -Sizzle.matchesSelector = function( node, expr ) { - return Sizzle( expr, null, null, [node] ).length > 0; -}; - -Sizzle.find = function( expr, context, isXML ) { - var set, i, len, match, type, left; - - if ( !expr ) { - return []; - } - - for ( i = 0, len = Expr.order.length; i < len; i++ ) { - type = Expr.order[i]; - - if ( (match = Expr.leftMatch[ type ].exec( expr )) ) { - left = match[1]; - match.splice( 1, 1 ); - - if ( left.substr( left.length - 1 ) !== "\\" ) { - match[1] = (match[1] || "").replace( rBackslash, "" ); - set = Expr.find[ type ]( match, context, isXML ); - - if ( set != null ) { - expr = expr.replace( Expr.match[ type ], "" ); - break; - } - } - } - } - - if ( !set ) { - set = typeof context.getElementsByTagName !== "undefined" ? - context.getElementsByTagName( "*" ) : - []; - } - - return { set: set, expr: expr }; -}; - -Sizzle.filter = function( expr, set, inplace, not ) { - var match, anyFound, - type, found, item, filter, left, - i, pass, - old = expr, - result = [], - curLoop = set, - isXMLFilter = set && set[0] && Sizzle.isXML( set[0] ); - - while ( expr && set.length ) { - for ( type in Expr.filter ) { - if ( (match = Expr.leftMatch[ type ].exec( expr )) != null && match[2] ) { - filter = Expr.filter[ type ]; - left = match[1]; - - anyFound = false; - - match.splice(1,1); - - if ( left.substr( left.length - 1 ) === "\\" ) { - continue; - } - - if ( curLoop === result ) { - result = []; - } - - if ( Expr.preFilter[ type ] ) { - match = Expr.preFilter[ type ]( match, curLoop, inplace, result, not, isXMLFilter ); - - if ( !match ) { - anyFound = found = true; - - } else if ( match === true ) { - continue; - } - } - - if ( match ) { - for ( i = 0; (item = curLoop[i]) != null; i++ ) { - if ( item ) { - found = filter( item, match, i, curLoop ); - pass = not ^ found; - - if ( inplace && found != null ) { - if ( pass ) { - anyFound = true; - - } else { - curLoop[i] = false; - } - - } else if ( pass ) { - result.push( item ); - anyFound = true; - } - } - } - } - - if ( found !== undefined ) { - if ( !inplace ) { - curLoop = result; - } - - expr = expr.replace( Expr.match[ type ], "" ); - - if ( !anyFound ) { - return []; - } - - break; - } - } - } - - // Improper expression - if ( expr === old ) { - if ( anyFound == null ) { - Sizzle.error( expr ); - - } else { - break; - } - } - - old = expr; - } - - return curLoop; -}; - -Sizzle.error = function( msg ) { - throw new Error( "Syntax error, unrecognized expression: " + msg ); -}; - -/** - * Utility function for retreiving the text value of an array of DOM nodes - * @param {Array|Element} elem - */ -var getText = Sizzle.getText = function( elem ) { - var i, node, - nodeType = elem.nodeType, - ret = ""; - - if ( nodeType ) { - if ( nodeType === 1 || nodeType === 9 || nodeType === 11 ) { - // Use textContent || innerText for elements - if ( typeof elem.textContent === 'string' ) { - return elem.textContent; - } else if ( typeof elem.innerText === 'string' ) { - // Replace IE's carriage returns - return elem.innerText.replace( rReturn, '' ); - } else { - // Traverse it's children - for ( elem = elem.firstChild; elem; elem = elem.nextSibling) { - ret += getText( elem ); - } - } - } else if ( nodeType === 3 || nodeType === 4 ) { - return elem.nodeValue; - } - } else { - - // If no nodeType, this is expected to be an array - for ( i = 0; (node = elem[i]); i++ ) { - // Do not traverse comment nodes - if ( node.nodeType !== 8 ) { - ret += getText( node ); - } - } - } - return ret; -}; - -var Expr = Sizzle.selectors = { - order: [ "ID", "NAME", "TAG" ], - - match: { - ID: /#((?:[\w\u00c0-\uFFFF\-]|\\.)+)/, - CLASS: /\.((?:[\w\u00c0-\uFFFF\-]|\\.)+)/, - NAME: /\[name=['"]*((?:[\w\u00c0-\uFFFF\-]|\\.)+)['"]*\]/, - ATTR: /\[\s*((?:[\w\u00c0-\uFFFF\-]|\\.)+)\s*(?:(\S?=)\s*(?:(['"])(.*?)\3|(#?(?:[\w\u00c0-\uFFFF\-]|\\.)*)|)|)\s*\]/, - TAG: /^((?:[\w\u00c0-\uFFFF\*\-]|\\.)+)/, - CHILD: /:(only|nth|last|first)-child(?:\(\s*(even|odd|(?:[+\-]?\d+|(?:[+\-]?\d*)?n\s*(?:[+\-]\s*\d+)?))\s*\))?/, - POS: /:(nth|eq|gt|lt|first|last|even|odd)(?:\((\d*)\))?(?=[^\-]|$)/, - PSEUDO: /:((?:[\w\u00c0-\uFFFF\-]|\\.)+)(?:\((['"]?)((?:\([^\)]+\)|[^\(\)]*)+)\2\))?/ - }, - - leftMatch: {}, - - attrMap: { - "class": "className", - "for": "htmlFor" - }, - - attrHandle: { - href: function( elem ) { - return elem.getAttribute( "href" ); - }, - type: function( elem ) { - return elem.getAttribute( "type" ); - } - }, - - relative: { - "+": function(checkSet, part){ - var isPartStr = typeof part === "string", - isTag = isPartStr && !rNonWord.test( part ), - isPartStrNotTag = isPartStr && !isTag; - - if ( isTag ) { - part = part.toLowerCase(); - } - - for ( var i = 0, l = checkSet.length, elem; i < l; i++ ) { - if ( (elem = checkSet[i]) ) { - while ( (elem = elem.previousSibling) && elem.nodeType !== 1 ) {} - - checkSet[i] = isPartStrNotTag || elem && elem.nodeName.toLowerCase() === part ? - elem || false : - elem === part; - } - } - - if ( isPartStrNotTag ) { - Sizzle.filter( part, checkSet, true ); - } - }, - - ">": function( checkSet, part ) { - var elem, - isPartStr = typeof part === "string", - i = 0, - l = checkSet.length; - - if ( isPartStr && !rNonWord.test( part ) ) { - part = part.toLowerCase(); - - for ( ; i < l; i++ ) { - elem = checkSet[i]; - - if ( elem ) { - var parent = elem.parentNode; - checkSet[i] = parent.nodeName.toLowerCase() === part ? parent : false; - } - } - - } else { - for ( ; i < l; i++ ) { - elem = checkSet[i]; - - if ( elem ) { - checkSet[i] = isPartStr ? - elem.parentNode : - elem.parentNode === part; - } - } - - if ( isPartStr ) { - Sizzle.filter( part, checkSet, true ); - } - } - }, - - "": function(checkSet, part, isXML){ - var nodeCheck, - doneName = done++, - checkFn = dirCheck; - - if ( typeof part === "string" && !rNonWord.test( part ) ) { - part = part.toLowerCase(); - nodeCheck = part; - checkFn = dirNodeCheck; - } - - checkFn( "parentNode", part, doneName, checkSet, nodeCheck, isXML ); - }, - - "~": function( checkSet, part, isXML ) { - var nodeCheck, - doneName = done++, - checkFn = dirCheck; - - if ( typeof part === "string" && !rNonWord.test( part ) ) { - part = part.toLowerCase(); - nodeCheck = part; - checkFn = dirNodeCheck; - } - - checkFn( "previousSibling", part, doneName, checkSet, nodeCheck, isXML ); - } - }, - - find: { - ID: function( match, context, isXML ) { - if ( typeof context.getElementById !== "undefined" && !isXML ) { - var m = context.getElementById(match[1]); - // Check parentNode to catch when Blackberry 4.6 returns - // nodes that are no longer in the document #6963 - return m && m.parentNode ? [m] : []; - } - }, - - NAME: function( match, context ) { - if ( typeof context.getElementsByName !== "undefined" ) { - var ret = [], - results = context.getElementsByName( match[1] ); - - for ( var i = 0, l = results.length; i < l; i++ ) { - if ( results[i].getAttribute("name") === match[1] ) { - ret.push( results[i] ); - } - } - - return ret.length === 0 ? null : ret; - } - }, - - TAG: function( match, context ) { - if ( typeof context.getElementsByTagName !== "undefined" ) { - return context.getElementsByTagName( match[1] ); - } - } - }, - preFilter: { - CLASS: function( match, curLoop, inplace, result, not, isXML ) { - match = " " + match[1].replace( rBackslash, "" ) + " "; - - if ( isXML ) { - return match; - } - - for ( var i = 0, elem; (elem = curLoop[i]) != null; i++ ) { - if ( elem ) { - if ( not ^ (elem.className && (" " + elem.className + " ").replace(/[\t\n\r]/g, " ").indexOf(match) >= 0) ) { - if ( !inplace ) { - result.push( elem ); - } - - } else if ( inplace ) { - curLoop[i] = false; - } - } - } - - return false; - }, - - ID: function( match ) { - return match[1].replace( rBackslash, "" ); - }, - - TAG: function( match, curLoop ) { - return match[1].replace( rBackslash, "" ).toLowerCase(); - }, - - CHILD: function( match ) { - if ( match[1] === "nth" ) { - if ( !match[2] ) { - Sizzle.error( match[0] ); - } - - match[2] = match[2].replace(/^\+|\s*/g, ''); - - // parse equations like 'even', 'odd', '5', '2n', '3n+2', '4n-1', '-n+6' - var test = /(-?)(\d*)(?:n([+\-]?\d*))?/.exec( - match[2] === "even" && "2n" || match[2] === "odd" && "2n+1" || - !/\D/.test( match[2] ) && "0n+" + match[2] || match[2]); - - // calculate the numbers (first)n+(last) including if they are negative - match[2] = (test[1] + (test[2] || 1)) - 0; - match[3] = test[3] - 0; - } - else if ( match[2] ) { - Sizzle.error( match[0] ); - } - - // TODO: Move to normal caching system - match[0] = done++; - - return match; - }, - - ATTR: function( match, curLoop, inplace, result, not, isXML ) { - var name = match[1] = match[1].replace( rBackslash, "" ); - - if ( !isXML && Expr.attrMap[name] ) { - match[1] = Expr.attrMap[name]; - } - - // Handle if an un-quoted value was used - match[4] = ( match[4] || match[5] || "" ).replace( rBackslash, "" ); - - if ( match[2] === "~=" ) { - match[4] = " " + match[4] + " "; - } - - return match; - }, - - PSEUDO: function( match, curLoop, inplace, result, not ) { - if ( match[1] === "not" ) { - // If we're dealing with a complex expression, or a simple one - if ( ( chunker.exec(match[3]) || "" ).length > 1 || /^\w/.test(match[3]) ) { - match[3] = Sizzle(match[3], null, null, curLoop); - - } else { - var ret = Sizzle.filter(match[3], curLoop, inplace, true ^ not); - - if ( !inplace ) { - result.push.apply( result, ret ); - } - - return false; - } - - } else if ( Expr.match.POS.test( match[0] ) || Expr.match.CHILD.test( match[0] ) ) { - return true; - } - - return match; - }, - - POS: function( match ) { - match.unshift( true ); - - return match; - } - }, - - filters: { - enabled: function( elem ) { - return elem.disabled === false && elem.type !== "hidden"; - }, - - disabled: function( elem ) { - return elem.disabled === true; - }, - - checked: function( elem ) { - return elem.checked === true; - }, - - selected: function( elem ) { - // Accessing this property makes selected-by-default - // options in Safari work properly - if ( elem.parentNode ) { - elem.parentNode.selectedIndex; - } - - return elem.selected === true; - }, - - parent: function( elem ) { - return !!elem.firstChild; - }, - - empty: function( elem ) { - return !elem.firstChild; - }, - - has: function( elem, i, match ) { - return !!Sizzle( match[3], elem ).length; - }, - - header: function( elem ) { - return (/h\d/i).test( elem.nodeName ); - }, - - text: function( elem ) { - var attr = elem.getAttribute( "type" ), type = elem.type; - // IE6 and 7 will map elem.type to 'text' for new HTML5 types (search, etc) - // use getAttribute instead to test this case - return elem.nodeName.toLowerCase() === "input" && "text" === type && ( attr === type || attr === null ); - }, - - radio: function( elem ) { - return elem.nodeName.toLowerCase() === "input" && "radio" === elem.type; - }, - - checkbox: function( elem ) { - return elem.nodeName.toLowerCase() === "input" && "checkbox" === elem.type; - }, - - file: function( elem ) { - return elem.nodeName.toLowerCase() === "input" && "file" === elem.type; - }, - - password: function( elem ) { - return elem.nodeName.toLowerCase() === "input" && "password" === elem.type; - }, - - submit: function( elem ) { - var name = elem.nodeName.toLowerCase(); - return (name === "input" || name === "button") && "submit" === elem.type; - }, - - image: function( elem ) { - return elem.nodeName.toLowerCase() === "input" && "image" === elem.type; - }, - - reset: function( elem ) { - var name = elem.nodeName.toLowerCase(); - return (name === "input" || name === "button") && "reset" === elem.type; - }, - - button: function( elem ) { - var name = elem.nodeName.toLowerCase(); - return name === "input" && "button" === elem.type || name === "button"; - }, - - input: function( elem ) { - return (/input|select|textarea|button/i).test( elem.nodeName ); - }, - - focus: function( elem ) { - return elem === elem.ownerDocument.activeElement; - } - }, - setFilters: { - first: function( elem, i ) { - return i === 0; - }, - - last: function( elem, i, match, array ) { - return i === array.length - 1; - }, - - even: function( elem, i ) { - return i % 2 === 0; - }, - - odd: function( elem, i ) { - return i % 2 === 1; - }, - - lt: function( elem, i, match ) { - return i < match[3] - 0; - }, - - gt: function( elem, i, match ) { - return i > match[3] - 0; - }, - - nth: function( elem, i, match ) { - return match[3] - 0 === i; - }, - - eq: function( elem, i, match ) { - return match[3] - 0 === i; - } - }, - filter: { - PSEUDO: function( elem, match, i, array ) { - var name = match[1], - filter = Expr.filters[ name ]; - - if ( filter ) { - return filter( elem, i, match, array ); - - } else if ( name === "contains" ) { - return (elem.textContent || elem.innerText || getText([ elem ]) || "").indexOf(match[3]) >= 0; - - } else if ( name === "not" ) { - var not = match[3]; - - for ( var j = 0, l = not.length; j < l; j++ ) { - if ( not[j] === elem ) { - return false; - } - } - - return true; - - } else { - Sizzle.error( name ); - } - }, - - CHILD: function( elem, match ) { - var first, last, - doneName, parent, cache, - count, diff, - type = match[1], - node = elem; - - switch ( type ) { - case "only": - case "first": - while ( (node = node.previousSibling) ) { - if ( node.nodeType === 1 ) { - return false; - } - } - - if ( type === "first" ) { - return true; - } - - node = elem; - - /* falls through */ - case "last": - while ( (node = node.nextSibling) ) { - if ( node.nodeType === 1 ) { - return false; - } - } - - return true; - - case "nth": - first = match[2]; - last = match[3]; - - if ( first === 1 && last === 0 ) { - return true; - } - - doneName = match[0]; - parent = elem.parentNode; - - if ( parent && (parent[ expando ] !== doneName || !elem.nodeIndex) ) { - count = 0; - - for ( node = parent.firstChild; node; node = node.nextSibling ) { - if ( node.nodeType === 1 ) { - node.nodeIndex = ++count; - } - } - - parent[ expando ] = doneName; - } - - diff = elem.nodeIndex - last; - - if ( first === 0 ) { - return diff === 0; - - } else { - return ( diff % first === 0 && diff / first >= 0 ); - } - } - }, - - ID: function( elem, match ) { - return elem.nodeType === 1 && elem.getAttribute("id") === match; - }, - - TAG: function( elem, match ) { - return (match === "*" && elem.nodeType === 1) || !!elem.nodeName && elem.nodeName.toLowerCase() === match; - }, - - CLASS: function( elem, match ) { - return (" " + (elem.className || elem.getAttribute("class")) + " ") - .indexOf( match ) > -1; - }, - - ATTR: function( elem, match ) { - var name = match[1], - result = Sizzle.attr ? - Sizzle.attr( elem, name ) : - Expr.attrHandle[ name ] ? - Expr.attrHandle[ name ]( elem ) : - elem[ name ] != null ? - elem[ name ] : - elem.getAttribute( name ), - value = result + "", - type = match[2], - check = match[4]; - - return result == null ? - type === "!=" : - !type && Sizzle.attr ? - result != null : - type === "=" ? - value === check : - type === "*=" ? - value.indexOf(check) >= 0 : - type === "~=" ? - (" " + value + " ").indexOf(check) >= 0 : - !check ? - value && result !== false : - type === "!=" ? - value !== check : - type === "^=" ? - value.indexOf(check) === 0 : - type === "$=" ? - value.substr(value.length - check.length) === check : - type === "|=" ? - value === check || value.substr(0, check.length + 1) === check + "-" : - false; - }, - - POS: function( elem, match, i, array ) { - var name = match[2], - filter = Expr.setFilters[ name ]; - - if ( filter ) { - return filter( elem, i, match, array ); - } - } - } -}; - -var origPOS = Expr.match.POS, - fescape = function(all, num){ - return "\\" + (num - 0 + 1); - }; - -for ( var type in Expr.match ) { - Expr.match[ type ] = new RegExp( Expr.match[ type ].source + (/(?![^\[]*\])(?![^\(]*\))/.source) ); - Expr.leftMatch[ type ] = new RegExp( /(^(?:.|\r|\n)*?)/.source + Expr.match[ type ].source.replace(/\\(\d+)/g, fescape) ); -} -// Expose origPOS -// "global" as in regardless of relation to brackets/parens -Expr.match.globalPOS = origPOS; - -var makeArray = function( array, results ) { - array = Array.prototype.slice.call( array, 0 ); - - if ( results ) { - results.push.apply( results, array ); - return results; - } - - return array; -}; - -// Perform a simple check to determine if the browser is capable of -// converting a NodeList to an array using builtin methods. -// Also verifies that the returned array holds DOM nodes -// (which is not the case in the Blackberry browser) -try { - Array.prototype.slice.call( document.documentElement.childNodes, 0 )[0].nodeType; - -// Provide a fallback method if it does not work -} catch( e ) { - makeArray = function( array, results ) { - var i = 0, - ret = results || []; - - if ( toString.call(array) === "[object Array]" ) { - Array.prototype.push.apply( ret, array ); - - } else { - if ( typeof array.length === "number" ) { - for ( var l = array.length; i < l; i++ ) { - ret.push( array[i] ); - } - - } else { - for ( ; array[i]; i++ ) { - ret.push( array[i] ); - } - } - } - - return ret; - }; -} - -var sortOrder, siblingCheck; - -if ( document.documentElement.compareDocumentPosition ) { - sortOrder = function( a, b ) { - if ( a === b ) { - hasDuplicate = true; - return 0; - } - - if ( !a.compareDocumentPosition || !b.compareDocumentPosition ) { - return a.compareDocumentPosition ? -1 : 1; - } - - return a.compareDocumentPosition(b) & 4 ? -1 : 1; - }; - -} else { - sortOrder = function( a, b ) { - // The nodes are identical, we can exit early - if ( a === b ) { - hasDuplicate = true; - return 0; - - // Fallback to using sourceIndex (in IE) if it's available on both nodes - } else if ( a.sourceIndex && b.sourceIndex ) { - return a.sourceIndex - b.sourceIndex; - } - - var al, bl, - ap = [], - bp = [], - aup = a.parentNode, - bup = b.parentNode, - cur = aup; - - // If the nodes are siblings (or identical) we can do a quick check - if ( aup === bup ) { - return siblingCheck( a, b ); - - // If no parents were found then the nodes are disconnected - } else if ( !aup ) { - return -1; - - } else if ( !bup ) { - return 1; - } - - // Otherwise they're somewhere else in the tree so we need - // to build up a full list of the parentNodes for comparison - while ( cur ) { - ap.unshift( cur ); - cur = cur.parentNode; - } - - cur = bup; - - while ( cur ) { - bp.unshift( cur ); - cur = cur.parentNode; - } - - al = ap.length; - bl = bp.length; - - // Start walking down the tree looking for a discrepancy - for ( var i = 0; i < al && i < bl; i++ ) { - if ( ap[i] !== bp[i] ) { - return siblingCheck( ap[i], bp[i] ); - } - } - - // We ended someplace up the tree so do a sibling check - return i === al ? - siblingCheck( a, bp[i], -1 ) : - siblingCheck( ap[i], b, 1 ); - }; - - siblingCheck = function( a, b, ret ) { - if ( a === b ) { - return ret; - } - - var cur = a.nextSibling; - - while ( cur ) { - if ( cur === b ) { - return -1; - } - - cur = cur.nextSibling; - } - - return 1; - }; -} - -// Check to see if the browser returns elements by name when -// querying by getElementById (and provide a workaround) -(function(){ - // We're going to inject a fake input element with a specified name - var form = document.createElement("div"), - id = "script" + (new Date()).getTime(), - root = document.documentElement; - - form.innerHTML = ""; - - // Inject it into the root element, check its status, and remove it quickly - root.insertBefore( form, root.firstChild ); - - // The workaround has to do additional checks after a getElementById - // Which slows things down for other browsers (hence the branching) - if ( document.getElementById( id ) ) { - Expr.find.ID = function( match, context, isXML ) { - if ( typeof context.getElementById !== "undefined" && !isXML ) { - var m = context.getElementById(match[1]); - - return m ? - m.id === match[1] || typeof m.getAttributeNode !== "undefined" && m.getAttributeNode("id").nodeValue === match[1] ? - [m] : - undefined : - []; - } - }; - - Expr.filter.ID = function( elem, match ) { - var node = typeof elem.getAttributeNode !== "undefined" && elem.getAttributeNode("id"); - - return elem.nodeType === 1 && node && node.nodeValue === match; - }; - } - - root.removeChild( form ); - - // release memory in IE - root = form = null; -})(); - -(function(){ - // Check to see if the browser returns only elements - // when doing getElementsByTagName("*") - - // Create a fake element - var div = document.createElement("div"); - div.appendChild( document.createComment("") ); - - // Make sure no comments are found - if ( div.getElementsByTagName("*").length > 0 ) { - Expr.find.TAG = function( match, context ) { - var results = context.getElementsByTagName( match[1] ); - - // Filter out possible comments - if ( match[1] === "*" ) { - var tmp = []; - - for ( var i = 0; results[i]; i++ ) { - if ( results[i].nodeType === 1 ) { - tmp.push( results[i] ); - } - } - - results = tmp; - } - - return results; - }; - } - - // Check to see if an attribute returns normalized href attributes - div.innerHTML = ""; - - if ( div.firstChild && typeof div.firstChild.getAttribute !== "undefined" && - div.firstChild.getAttribute("href") !== "#" ) { - - Expr.attrHandle.href = function( elem ) { - return elem.getAttribute( "href", 2 ); - }; - } - - // release memory in IE - div = null; -})(); - -if ( document.querySelectorAll ) { - (function(){ - var oldSizzle = Sizzle, - div = document.createElement("div"), - id = "__sizzle__"; - - div.innerHTML = "

"; - - // Safari can't handle uppercase or unicode characters when - // in quirks mode. - if ( div.querySelectorAll && div.querySelectorAll(".TEST").length === 0 ) { - return; - } - - Sizzle = function( query, context, extra, seed ) { - context = context || document; - - // Only use querySelectorAll on non-XML documents - // (ID selectors don't work in non-HTML documents) - if ( !seed && !Sizzle.isXML(context) ) { - // See if we find a selector to speed up - var match = /^(\w+$)|^\.([\w\-]+$)|^#([\w\-]+$)/.exec( query ); - - if ( match && (context.nodeType === 1 || context.nodeType === 9) ) { - // Speed-up: Sizzle("TAG") - if ( match[1] ) { - return makeArray( context.getElementsByTagName( query ), extra ); - - // Speed-up: Sizzle(".CLASS") - } else if ( match[2] && Expr.find.CLASS && context.getElementsByClassName ) { - return makeArray( context.getElementsByClassName( match[2] ), extra ); - } - } - - if ( context.nodeType === 9 ) { - // Speed-up: Sizzle("body") - // The body element only exists once, optimize finding it - if ( query === "body" && context.body ) { - return makeArray( [ context.body ], extra ); - - // Speed-up: Sizzle("#ID") - } else if ( match && match[3] ) { - var elem = context.getElementById( match[3] ); - - // Check parentNode to catch when Blackberry 4.6 returns - // nodes that are no longer in the document #6963 - if ( elem && elem.parentNode ) { - // Handle the case where IE and Opera return items - // by name instead of ID - if ( elem.id === match[3] ) { - return makeArray( [ elem ], extra ); - } - - } else { - return makeArray( [], extra ); - } - } - - try { - return makeArray( context.querySelectorAll(query), extra ); - } catch(qsaError) {} - - // qSA works strangely on Element-rooted queries - // We can work around this by specifying an extra ID on the root - // and working up from there (Thanks to Andrew Dupont for the technique) - // IE 8 doesn't work on object elements - } else if ( context.nodeType === 1 && context.nodeName.toLowerCase() !== "object" ) { - var oldContext = context, - old = context.getAttribute( "id" ), - nid = old || id, - hasParent = context.parentNode, - relativeHierarchySelector = /^\s*[+~]/.test( query ); - - if ( !old ) { - context.setAttribute( "id", nid ); - } else { - nid = nid.replace( /'/g, "\\$&" ); - } - if ( relativeHierarchySelector && hasParent ) { - context = context.parentNode; - } - - try { - if ( !relativeHierarchySelector || hasParent ) { - return makeArray( context.querySelectorAll( "[id='" + nid + "'] " + query ), extra ); - } - - } catch(pseudoError) { - } finally { - if ( !old ) { - oldContext.removeAttribute( "id" ); - } - } - } - } - - return oldSizzle(query, context, extra, seed); - }; - - for ( var prop in oldSizzle ) { - Sizzle[ prop ] = oldSizzle[ prop ]; - } - - // release memory in IE - div = null; - })(); -} - -(function(){ - var html = document.documentElement, - matches = html.matchesSelector || html.mozMatchesSelector || html.webkitMatchesSelector || html.msMatchesSelector; - - if ( matches ) { - // Check to see if it's possible to do matchesSelector - // on a disconnected node (IE 9 fails this) - var disconnectedMatch = !matches.call( document.createElement( "div" ), "div" ), - pseudoWorks = false; - - try { - // This should fail with an exception - // Gecko does not error, returns false instead - matches.call( document.documentElement, "[test!='']:sizzle" ); - - } catch( pseudoError ) { - pseudoWorks = true; - } - - Sizzle.matchesSelector = function( node, expr ) { - // Make sure that attribute selectors are quoted - expr = expr.replace(/\=\s*([^'"\]]*)\s*\]/g, "='$1']"); - - if ( !Sizzle.isXML( node ) ) { - try { - if ( pseudoWorks || !Expr.match.PSEUDO.test( expr ) && !/!=/.test( expr ) ) { - var ret = matches.call( node, expr ); - - // IE 9's matchesSelector returns false on disconnected nodes - if ( ret || !disconnectedMatch || - // As well, disconnected nodes are said to be in a document - // fragment in IE 9, so check for that - node.document && node.document.nodeType !== 11 ) { - return ret; - } - } - } catch(e) {} - } - - return Sizzle(expr, null, null, [node]).length > 0; - }; - } -})(); - -(function(){ - var div = document.createElement("div"); - - div.innerHTML = "
"; - - // Opera can't find a second classname (in 9.6) - // Also, make sure that getElementsByClassName actually exists - if ( !div.getElementsByClassName || div.getElementsByClassName("e").length === 0 ) { - return; - } - - // Safari caches class attributes, doesn't catch changes (in 3.2) - div.lastChild.className = "e"; - - if ( div.getElementsByClassName("e").length === 1 ) { - return; - } - - Expr.order.splice(1, 0, "CLASS"); - Expr.find.CLASS = function( match, context, isXML ) { - if ( typeof context.getElementsByClassName !== "undefined" && !isXML ) { - return context.getElementsByClassName(match[1]); - } - }; - - // release memory in IE - div = null; -})(); - -function dirNodeCheck( dir, cur, doneName, checkSet, nodeCheck, isXML ) { - for ( var i = 0, l = checkSet.length; i < l; i++ ) { - var elem = checkSet[i]; - - if ( elem ) { - var match = false; - - elem = elem[dir]; - - while ( elem ) { - if ( elem[ expando ] === doneName ) { - match = checkSet[elem.sizset]; - break; - } - - if ( elem.nodeType === 1 && !isXML ){ - elem[ expando ] = doneName; - elem.sizset = i; - } - - if ( elem.nodeName.toLowerCase() === cur ) { - match = elem; - break; - } - - elem = elem[dir]; - } - - checkSet[i] = match; - } - } -} - -function dirCheck( dir, cur, doneName, checkSet, nodeCheck, isXML ) { - for ( var i = 0, l = checkSet.length; i < l; i++ ) { - var elem = checkSet[i]; - - if ( elem ) { - var match = false; - - elem = elem[dir]; - - while ( elem ) { - if ( elem[ expando ] === doneName ) { - match = checkSet[elem.sizset]; - break; - } - - if ( elem.nodeType === 1 ) { - if ( !isXML ) { - elem[ expando ] = doneName; - elem.sizset = i; - } - - if ( typeof cur !== "string" ) { - if ( elem === cur ) { - match = true; - break; - } - - } else if ( Sizzle.filter( cur, [elem] ).length > 0 ) { - match = elem; - break; - } - } - - elem = elem[dir]; - } - - checkSet[i] = match; - } - } -} - -if ( document.documentElement.contains ) { - Sizzle.contains = function( a, b ) { - return a !== b && (a.contains ? a.contains(b) : true); - }; - -} else if ( document.documentElement.compareDocumentPosition ) { - Sizzle.contains = function( a, b ) { - return !!(a.compareDocumentPosition(b) & 16); - }; - -} else { - Sizzle.contains = function() { - return false; - }; -} - -Sizzle.isXML = function( elem ) { - // documentElement is verified for cases where it doesn't yet exist - // (such as loading iframes in IE - #4833) - var documentElement = (elem ? elem.ownerDocument || elem : 0).documentElement; - - return documentElement ? documentElement.nodeName !== "HTML" : false; -}; - -var posProcess = function( selector, context, seed ) { - var match, - tmpSet = [], - later = "", - root = context.nodeType ? [context] : context; - - // Position selectors must be done after the filter - // And so must :not(positional) so we move all PSEUDOs to the end - while ( (match = Expr.match.PSEUDO.exec( selector )) ) { - later += match[0]; - selector = selector.replace( Expr.match.PSEUDO, "" ); - } - - selector = Expr.relative[selector] ? selector + "*" : selector; - - for ( var i = 0, l = root.length; i < l; i++ ) { - Sizzle( selector, root[i], tmpSet, seed ); - } - - return Sizzle.filter( later, tmpSet ); -}; - -// EXPOSE -// Override sizzle attribute retrieval -Sizzle.attr = jQuery.attr; -Sizzle.selectors.attrMap = {}; -jQuery.find = Sizzle; -jQuery.expr = Sizzle.selectors; -jQuery.expr[":"] = jQuery.expr.filters; -jQuery.unique = Sizzle.uniqueSort; -jQuery.text = Sizzle.getText; -jQuery.isXMLDoc = Sizzle.isXML; -jQuery.contains = Sizzle.contains; - - -})(); - - -var runtil = /Until$/, - rparentsprev = /^(?:parents|prevUntil|prevAll)/, - // Note: This RegExp should be improved, or likely pulled from Sizzle - rmultiselector = /,/, - isSimple = /^.[^:#\[\.,]*$/, - slice = Array.prototype.slice, - POS = jQuery.expr.match.globalPOS, - // methods guaranteed to produce a unique set when starting from a unique set - guaranteedUnique = { - children: true, - contents: true, - next: true, - prev: true - }; - -jQuery.fn.extend({ - find: function( selector ) { - var self = this, - i, l; - - if ( typeof selector !== "string" ) { - return jQuery( selector ).filter(function() { - for ( i = 0, l = self.length; i < l; i++ ) { - if ( jQuery.contains( self[ i ], this ) ) { - return true; - } - } - }); - } - - var ret = this.pushStack( "", "find", selector ), - length, n, r; - - for ( i = 0, l = this.length; i < l; i++ ) { - length = ret.length; - jQuery.find( selector, this[i], ret ); - - if ( i > 0 ) { - // Make sure that the results are unique - for ( n = length; n < ret.length; n++ ) { - for ( r = 0; r < length; r++ ) { - if ( ret[r] === ret[n] ) { - ret.splice(n--, 1); - break; - } - } - } - } - } - - return ret; - }, - - has: function( target ) { - var targets = jQuery( target ); - return this.filter(function() { - for ( var i = 0, l = targets.length; i < l; i++ ) { - if ( jQuery.contains( this, targets[i] ) ) { - return true; - } - } - }); - }, - - not: function( selector ) { - return this.pushStack( winnow(this, selector, false), "not", selector); - }, - - filter: function( selector ) { - return this.pushStack( winnow(this, selector, true), "filter", selector ); - }, - - is: function( selector ) { - return !!selector && ( - typeof selector === "string" ? - // If this is a positional selector, check membership in the returned set - // so $("p:first").is("p:last") won't return true for a doc with two "p". - POS.test( selector ) ? - jQuery( selector, this.context ).index( this[0] ) >= 0 : - jQuery.filter( selector, this ).length > 0 : - this.filter( selector ).length > 0 ); - }, - - closest: function( selectors, context ) { - var ret = [], i, l, cur = this[0]; - - // Array (deprecated as of jQuery 1.7) - if ( jQuery.isArray( selectors ) ) { - var level = 1; - - while ( cur && cur.ownerDocument && cur !== context ) { - for ( i = 0; i < selectors.length; i++ ) { - - if ( jQuery( cur ).is( selectors[ i ] ) ) { - ret.push({ selector: selectors[ i ], elem: cur, level: level }); - } - } - - cur = cur.parentNode; - level++; - } - - return ret; - } - - // String - var pos = POS.test( selectors ) || typeof selectors !== "string" ? - jQuery( selectors, context || this.context ) : - 0; - - for ( i = 0, l = this.length; i < l; i++ ) { - cur = this[i]; - - while ( cur ) { - if ( pos ? pos.index(cur) > -1 : jQuery.find.matchesSelector(cur, selectors) ) { - ret.push( cur ); - break; - - } else { - cur = cur.parentNode; - if ( !cur || !cur.ownerDocument || cur === context || cur.nodeType === 11 ) { - break; - } - } - } - } - - ret = ret.length > 1 ? jQuery.unique( ret ) : ret; - - return this.pushStack( ret, "closest", selectors ); - }, - - // Determine the position of an element within - // the matched set of elements - index: function( elem ) { - - // No argument, return index in parent - if ( !elem ) { - return ( this[0] && this[0].parentNode ) ? this.prevAll().length : -1; - } - - // index in selector - if ( typeof elem === "string" ) { - return jQuery.inArray( this[0], jQuery( elem ) ); - } - - // Locate the position of the desired element - return jQuery.inArray( - // If it receives a jQuery object, the first element is used - elem.jquery ? elem[0] : elem, this ); - }, - - add: function( selector, context ) { - var set = typeof selector === "string" ? - jQuery( selector, context ) : - jQuery.makeArray( selector && selector.nodeType ? [ selector ] : selector ), - all = jQuery.merge( this.get(), set ); - - return this.pushStack( isDisconnected( set[0] ) || isDisconnected( all[0] ) ? - all : - jQuery.unique( all ) ); - }, - - andSelf: function() { - return this.add( this.prevObject ); - } -}); - -// A painfully simple check to see if an element is disconnected -// from a document (should be improved, where feasible). -function isDisconnected( node ) { - return !node || !node.parentNode || node.parentNode.nodeType === 11; -} - -jQuery.each({ - parent: function( elem ) { - var parent = elem.parentNode; - return parent && parent.nodeType !== 11 ? parent : null; - }, - parents: function( elem ) { - return jQuery.dir( elem, "parentNode" ); - }, - parentsUntil: function( elem, i, until ) { - return jQuery.dir( elem, "parentNode", until ); - }, - next: function( elem ) { - return jQuery.nth( elem, 2, "nextSibling" ); - }, - prev: function( elem ) { - return jQuery.nth( elem, 2, "previousSibling" ); - }, - nextAll: function( elem ) { - return jQuery.dir( elem, "nextSibling" ); - }, - prevAll: function( elem ) { - return jQuery.dir( elem, "previousSibling" ); - }, - nextUntil: function( elem, i, until ) { - return jQuery.dir( elem, "nextSibling", until ); - }, - prevUntil: function( elem, i, until ) { - return jQuery.dir( elem, "previousSibling", until ); - }, - siblings: function( elem ) { - return jQuery.sibling( ( elem.parentNode || {} ).firstChild, elem ); - }, - children: function( elem ) { - return jQuery.sibling( elem.firstChild ); - }, - contents: function( elem ) { - return jQuery.nodeName( elem, "iframe" ) ? - elem.contentDocument || elem.contentWindow.document : - jQuery.makeArray( elem.childNodes ); - } -}, function( name, fn ) { - jQuery.fn[ name ] = function( until, selector ) { - var ret = jQuery.map( this, fn, until ); - - if ( !runtil.test( name ) ) { - selector = until; - } - - if ( selector && typeof selector === "string" ) { - ret = jQuery.filter( selector, ret ); - } - - ret = this.length > 1 && !guaranteedUnique[ name ] ? jQuery.unique( ret ) : ret; - - if ( (this.length > 1 || rmultiselector.test( selector )) && rparentsprev.test( name ) ) { - ret = ret.reverse(); - } - - return this.pushStack( ret, name, slice.call( arguments ).join(",") ); - }; -}); - -jQuery.extend({ - filter: function( expr, elems, not ) { - if ( not ) { - expr = ":not(" + expr + ")"; - } - - return elems.length === 1 ? - jQuery.find.matchesSelector(elems[0], expr) ? [ elems[0] ] : [] : - jQuery.find.matches(expr, elems); - }, - - dir: function( elem, dir, until ) { - var matched = [], - cur = elem[ dir ]; - - while ( cur && cur.nodeType !== 9 && (until === undefined || cur.nodeType !== 1 || !jQuery( cur ).is( until )) ) { - if ( cur.nodeType === 1 ) { - matched.push( cur ); - } - cur = cur[dir]; - } - return matched; - }, - - nth: function( cur, result, dir, elem ) { - result = result || 1; - var num = 0; - - for ( ; cur; cur = cur[dir] ) { - if ( cur.nodeType === 1 && ++num === result ) { - break; - } - } - - return cur; - }, - - sibling: function( n, elem ) { - var r = []; - - for ( ; n; n = n.nextSibling ) { - if ( n.nodeType === 1 && n !== elem ) { - r.push( n ); - } - } - - return r; - } -}); - -// Implement the identical functionality for filter and not -function winnow( elements, qualifier, keep ) { - - // Can't pass null or undefined to indexOf in Firefox 4 - // Set to 0 to skip string check - qualifier = qualifier || 0; - - if ( jQuery.isFunction( qualifier ) ) { - return jQuery.grep(elements, function( elem, i ) { - var retVal = !!qualifier.call( elem, i, elem ); - return retVal === keep; - }); - - } else if ( qualifier.nodeType ) { - return jQuery.grep(elements, function( elem, i ) { - return ( elem === qualifier ) === keep; - }); - - } else if ( typeof qualifier === "string" ) { - var filtered = jQuery.grep(elements, function( elem ) { - return elem.nodeType === 1; - }); - - if ( isSimple.test( qualifier ) ) { - return jQuery.filter(qualifier, filtered, !keep); - } else { - qualifier = jQuery.filter( qualifier, filtered ); - } - } - - return jQuery.grep(elements, function( elem, i ) { - return ( jQuery.inArray( elem, qualifier ) >= 0 ) === keep; - }); -} - - - - -function createSafeFragment( document ) { - var list = nodeNames.split( "|" ), - safeFrag = document.createDocumentFragment(); - - if ( safeFrag.createElement ) { - while ( list.length ) { - safeFrag.createElement( - list.pop() - ); - } - } - return safeFrag; -} - -var nodeNames = "abbr|article|aside|audio|bdi|canvas|data|datalist|details|figcaption|figure|footer|" + - "header|hgroup|mark|meter|nav|output|progress|section|summary|time|video", - rinlinejQuery = / jQuery\d+="(?:\d+|null)"/g, - rleadingWhitespace = /^\s+/, - rxhtmlTag = /<(?!area|br|col|embed|hr|img|input|link|meta|param)(([\w:]+)[^>]*)\/>/ig, - rtagName = /<([\w:]+)/, - rtbody = /]", "i"), - // checked="checked" or checked - rchecked = /checked\s*(?:[^=]|=\s*.checked.)/i, - rscriptType = /\/(java|ecma)script/i, - rcleanScript = /^\s*", "" ], - legend: [ 1, "
", "
" ], - thead: [ 1, "", "
" ], - tr: [ 2, "", "
" ], - td: [ 3, "", "
" ], - col: [ 2, "", "
" ], - area: [ 1, "", "" ], - _default: [ 0, "", "" ] - }, - safeFragment = createSafeFragment( document ); - -wrapMap.optgroup = wrapMap.option; -wrapMap.tbody = wrapMap.tfoot = wrapMap.colgroup = wrapMap.caption = wrapMap.thead; -wrapMap.th = wrapMap.td; - -// IE can't serialize and