diff options
41 files changed, 277 insertions, 216 deletions
diff --git a/extra/mariabackup/backup_copy.cc b/extra/mariabackup/backup_copy.cc index 6a0674bf7f5..525481d5e9e 100644 --- a/extra/mariabackup/backup_copy.cc +++ b/extra/mariabackup/backup_copy.cc @@ -1782,7 +1782,7 @@ apply_log_finish() bool copy_back() { - bool ret; + bool ret = false; datadir_iter_t *it = NULL; datadir_node_t node; char *dst_dir; diff --git a/include/ilist.h b/include/ilist.h index 822f0334022..6e7219937dd 100644 --- a/include/ilist.h +++ b/include/ilist.h @@ -19,6 +19,8 @@ #ifndef ILIST_H #define ILIST_H +#include "my_dbug.h" + #include <cstddef> #include <iterator> @@ -73,11 +75,13 @@ public: typedef T *pointer; typedef T &reference; - Iterator(ListNode *node) noexcept : node_(node) {} + Iterator(ListNode *node) noexcept : node_(node) + { DBUG_ASSERT(node_ != nullptr); } Iterator &operator++() noexcept { node_= node_->next; + DBUG_ASSERT(node_ != nullptr); return *this; } Iterator operator++(int) noexcept @@ -90,6 +94,7 @@ public: Iterator &operator--() noexcept { node_= node_->prev; + DBUG_ASSERT(node_); return *this; } Iterator operator--(int) noexcept @@ -184,8 +189,8 @@ public: #ifndef DBUG_OFF ListNode *curr= pos.node_; - curr->prev= NULL; - curr->next= NULL; + curr->prev= nullptr; + curr->next= nullptr; #endif return next; diff --git a/mysql-test/main/type_datetime.result b/mysql-test/main/type_datetime.result index 6dbf7e58d7b..bb3e86b6543 100644 --- a/mysql-test/main/type_datetime.result +++ b/mysql-test/main/type_datetime.result @@ -57,6 +57,7 @@ select * from t1; t 0000-00-00 00:00:00 drop table t1; +SET TIMESTAMP=UNIX_TIMESTAMP('2020-08-11 00:00:01'); CREATE TABLE t1 (a timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP, b date, c time, d datetime); insert into t1 (b,c,d) values(now(),curtime(),now()); Warnings: @@ -65,6 +66,7 @@ select date_format(a,"%Y-%m-%d")=b,right(a+0,6)=c+0,a=d+0 from t1; date_format(a,"%Y-%m-%d")=b right(a+0,6)=c+0 a=d+0 1 1 1 drop table t1; +SET TIMESTAMP=DEFAULT; CREATE TABLE t1 (a datetime not null); insert into t1 values (0); select * from t1 where a is null; @@ -298,8 +300,10 @@ f2 f3 select f2 from t1 where DATE(f2) between "2001-4-15" AND "01-4-15"; f2 2001-04-15 00:00:00 +SET timestamp=UNIX_TIMESTAMP('2001-01-01 00:00:01'); SELECT 1 from dual where NOW() BETWEEN CURRENT_DATE() - INTERVAL 1 DAY AND CURRENT_DATE(); 1 +SET timestamp=DEFAULT; drop table t1; create table t1 (f1 date); insert into t1 values('01-01-01'),('01-01-02'),('01-01-03'); diff --git a/mysql-test/main/type_datetime.test b/mysql-test/main/type_datetime.test index c8ad240d817..4fddf1c1a74 100644 --- a/mysql-test/main/type_datetime.test +++ b/mysql-test/main/type_datetime.test @@ -32,10 +32,12 @@ drop table t1; # Test insert of now() and curtime() # +SET TIMESTAMP=UNIX_TIMESTAMP('2020-08-11 00:00:01'); CREATE TABLE t1 (a timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP, b date, c time, d datetime); insert into t1 (b,c,d) values(now(),curtime(),now()); select date_format(a,"%Y-%m-%d")=b,right(a+0,6)=c+0,a=d+0 from t1; drop table t1; +SET TIMESTAMP=DEFAULT; # # Test of datetime and not null @@ -201,6 +203,7 @@ drop table t1; # # Bug#16377: Wrong DATE/DATETIME comparison in BETWEEN function. # + create table t1 (f1 date, f2 datetime, f3 timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP); insert into t1 values('2001-01-01','2001-01-01 01:01:01','2001-01-01 01:01:01'); insert into t1 values('2001-02-05','2001-02-05 00:00:00','2001-02-05 01:01:01'); @@ -214,7 +217,9 @@ select f1, f2, f3 from t1 where cast(f1 as datetime) between f2 and select f2 from t1 where '2001-04-10 12:34:56' between f2 and '01-05-01'; select f2, f3 from t1 where '01-03-10' between f2 and f3; select f2 from t1 where DATE(f2) between "2001-4-15" AND "01-4-15"; +SET timestamp=UNIX_TIMESTAMP('2001-01-01 00:00:01'); SELECT 1 from dual where NOW() BETWEEN CURRENT_DATE() - INTERVAL 1 DAY AND CURRENT_DATE(); +SET timestamp=DEFAULT; drop table t1; # diff --git a/mysql-test/suite/innodb/include/alter_table_pk_no_sort.inc b/mysql-test/suite/innodb/include/alter_table_pk_no_sort.inc index 6a2fcd15be0..61e304a7626 100644 --- a/mysql-test/suite/innodb/include/alter_table_pk_no_sort.inc +++ b/mysql-test/suite/innodb/include/alter_table_pk_no_sort.inc @@ -263,3 +263,10 @@ create table t1(o1 int, o2 int, o3 int, primary key(o1,o2,o3)) engine = innodb; insert into t1 values(1,1,2),(2,2,1); alter table t1 drop primary key, add primary key(o1), lock=none; drop table t1; + +# pk(o1,o2) to pk(o1,o2,autoinc) must not sort +create table t1(o1 int, o2 int, primary key(o1,o2)) engine = innodb; +insert into t1 values(1,1),(2,1); +alter table t1 drop primary key, add column a int unique auto_increment, +add primary key(o1,o2,a), algorithm=inplace; +drop table t1; diff --git a/mysql-test/suite/innodb/r/alter_table.result b/mysql-test/suite/innodb/r/alter_table.result index 0cfd3096f3f..c51c14314f1 100644 --- a/mysql-test/suite/innodb/r/alter_table.result +++ b/mysql-test/suite/innodb/r/alter_table.result @@ -53,6 +53,13 @@ ALTER TABLE t1 DROP a; ERROR HY000: Cannot drop index 'a': needed in a foreign key constraint ALTER TABLE t1 ADD c INT; DROP TABLE t1, tx; +# +# MDEV-14119 Assertion cmp_rec_rec() on ALTER TABLE +# +CREATE TABLE t1(a INT NOT NULL UNIQUE) ENGINE=InnoDB; +INSERT INTO t1 SELECT * FROM seq_1_to_128; +ALTER TABLE t1 ADD b TINYINT AUTO_INCREMENT PRIMARY KEY, DROP KEY a; +DROP TABLE t1; create table t1 (a int) transactional=1 engine=aria; create table t2 (a int) transactional=1 engine=innodb; show create table t1; diff --git a/mysql-test/suite/innodb/r/innodb-64k.result b/mysql-test/suite/innodb/r/innodb-64k.result index 8f8e031bce2..f8dad893d0e 100644 --- a/mysql-test/suite/innodb/r/innodb-64k.result +++ b/mysql-test/suite/innodb/r/innodb-64k.result @@ -1081,3 +1081,10 @@ update t2 set col145=@b; COMMIT; drop table t2; DROP TABLE t1; +# +# MDEV-19526 heap number overflow +# +CREATE TABLE t1(a SMALLINT NOT NULL UNIQUE AUTO_INCREMENT, KEY(a)) +ENGINE=InnoDB; +INSERT INTO t1 (a) SELECT seq FROM seq_1_to_8191; +DROP TABLE t1; diff --git a/mysql-test/suite/innodb/r/innodb-index-debug.result b/mysql-test/suite/innodb/r/innodb-index-debug.result index 5d161e5e6ca..daef31d2caa 100644 --- a/mysql-test/suite/innodb/r/innodb-index-debug.result +++ b/mysql-test/suite/innodb/r/innodb-index-debug.result @@ -323,4 +323,9 @@ create table t1(o1 int, o2 int, o3 int, primary key(o1,o2,o3)) engine = innodb; insert into t1 values(1,1,2),(2,2,1); alter table t1 drop primary key, add primary key(o1), lock=none; drop table t1; +create table t1(o1 int, o2 int, primary key(o1,o2)) engine = innodb; +insert into t1 values(1,1),(2,1); +alter table t1 drop primary key, add column a int unique auto_increment, +add primary key(o1,o2,a), algorithm=inplace; +drop table t1; SET DEBUG_DBUG = @saved_debug_dbug; diff --git a/mysql-test/suite/innodb/r/innodb-index.result b/mysql-test/suite/innodb/r/innodb-index.result index 4eba99950c7..7e58bfe38e5 100644 --- a/mysql-test/suite/innodb/r/innodb-index.result +++ b/mysql-test/suite/innodb/r/innodb-index.result @@ -1907,6 +1907,11 @@ create table t1(o1 int, o2 int, o3 int, primary key(o1,o2,o3)) engine = innodb; insert into t1 values(1,1,2),(2,2,1); alter table t1 drop primary key, add primary key(o1), lock=none; drop table t1; +create table t1(o1 int, o2 int, primary key(o1,o2)) engine = innodb; +insert into t1 values(1,1),(2,1); +alter table t1 drop primary key, add column a int unique auto_increment, +add primary key(o1,o2,a), algorithm=inplace; +drop table t1; # # MDEV-15325 Incomplete validation of missing tablespace during recovery # diff --git a/mysql-test/suite/innodb/t/alter_table.test b/mysql-test/suite/innodb/t/alter_table.test index a8b52732c91..55c8626ae14 100644 --- a/mysql-test/suite/innodb/t/alter_table.test +++ b/mysql-test/suite/innodb/t/alter_table.test @@ -1,4 +1,5 @@ --source include/have_innodb.inc +--source include/have_sequence.inc # # MDEV-11995 ALTER TABLE proceeds despite reporting ER_TOO_LONG_KEY error # @@ -60,6 +61,14 @@ ALTER TABLE t1 DROP a; ALTER TABLE t1 ADD c INT; DROP TABLE t1, tx; +--echo # +--echo # MDEV-14119 Assertion cmp_rec_rec() on ALTER TABLE +--echo # +CREATE TABLE t1(a INT NOT NULL UNIQUE) ENGINE=InnoDB; +INSERT INTO t1 SELECT * FROM seq_1_to_128; +ALTER TABLE t1 ADD b TINYINT AUTO_INCREMENT PRIMARY KEY, DROP KEY a; +DROP TABLE t1; + # # Check that innodb supports transactional=1 # diff --git a/mysql-test/suite/innodb/t/innodb-64k.test b/mysql-test/suite/innodb/t/innodb-64k.test index b091eee6d57..62d7b929ba1 100644 --- a/mysql-test/suite/innodb/t/innodb-64k.test +++ b/mysql-test/suite/innodb/t/innodb-64k.test @@ -2,6 +2,7 @@ # Tests for setting innodb-page-size=64k; --source include/have_innodb.inc --source include/have_innodb_64k.inc +--source include/have_sequence.inc call mtr.add_suppression('InnoDB: Cannot add field.*because after adding it, the row size is'); @@ -638,3 +639,11 @@ COMMIT; drop table t2; DROP TABLE t1; + +--echo # +--echo # MDEV-19526 heap number overflow +--echo # +CREATE TABLE t1(a SMALLINT NOT NULL UNIQUE AUTO_INCREMENT, KEY(a)) +ENGINE=InnoDB; +INSERT INTO t1 (a) SELECT seq FROM seq_1_to_8191; +DROP TABLE t1; diff --git a/mysql-test/suite/sys_vars/r/sysvars_innodb.result b/mysql-test/suite/sys_vars/r/sysvars_innodb.result index 9463f946e66..183dab52cbf 100644 --- a/mysql-test/suite/sys_vars/r/sysvars_innodb.result +++ b/mysql-test/suite/sys_vars/r/sysvars_innodb.result @@ -410,7 +410,7 @@ SESSION_VALUE NULL DEFAULT_VALUE zlib VARIABLE_SCOPE GLOBAL VARIABLE_TYPE ENUM -VARIABLE_COMMENT Compression algorithm used on page compression. One of: none, zlib, lz4, lzo, lzma, or bzip2 +VARIABLE_COMMENT Compression algorithm used on page compression. One of: none, zlib, lz4, lzo, lzma, bzip2, or snappy NUMERIC_MIN_VALUE NULL NUMERIC_MAX_VALUE NULL NUMERIC_BLOCK_SIZE NULL diff --git a/plugin/handler_socket/CMakeLists.txt b/plugin/handler_socket/CMakeLists.txt index 329ff58d7f2..5a1925b40e0 100644 --- a/plugin/handler_socket/CMakeLists.txt +++ b/plugin/handler_socket/CMakeLists.txt @@ -1,7 +1,8 @@ -IF(WIN32) +IF(WIN32 OR WITHOUT_SERVER) # Handlersocket does not compile on Windows, compiles but does - # not start on FreeBSD. + # not start on FreeBSD. + # It is a server plugin and disable it explicitly here. RETURN() ENDIF() diff --git a/plugin/server_audit/server_audit.c b/plugin/server_audit/server_audit.c index c8b22eee20c..4a6757aee90 100644 --- a/plugin/server_audit/server_audit.c +++ b/plugin/server_audit/server_audit.c @@ -1431,7 +1431,6 @@ static size_t escape_string_hide_passwords(const char *str, unsigned int len, const char *res_start= result; const char *res_end= result + result_len - 2; size_t d_len; - char b_char; while (len) { @@ -1469,27 +1468,28 @@ static size_t escape_string_hide_passwords(const char *str, unsigned int len, if (*next_s) { - memmove(result + d_len, "*****", 5); + const char b_char= *next_s++; + memset(result + d_len, '*', 5); result+= d_len + 5; - b_char= *(next_s++); - } - else - result+= d_len; - while (*next_s) - { - if (*next_s == b_char) - { - ++next_s; - break; - } - if (*next_s == '\\') + while (*next_s) { - if (next_s[1]) - next_s++; + if (*next_s == b_char) + { + ++next_s; + break; + } + if (*next_s == '\\') + { + if (next_s[1]) + next_s++; + } + next_s++; } - next_s++; } + else + result+= d_len; + len-= (uint)(next_s - str); str= next_s; continue; @@ -1497,19 +1497,23 @@ static size_t escape_string_hide_passwords(const char *str, unsigned int len, no_password: if (result >= res_end) break; - if ((b_char= escaped_char(*str))) + else { - if (result+1 >= res_end) - break; - *(result++)= '\\'; - *(result++)= b_char; + const char b_char= escaped_char(*str); + if (b_char) + { + if (result+1 >= res_end) + break; + *(result++)= '\\'; + *(result++)= b_char; + } + else if (is_space(*str)) + *(result++)= ' '; + else + *(result++)= *str; + str++; + len--; } - else if (is_space(*str)) - *(result++)= ' '; - else - *(result++)= *str; - str++; - len--; } *result= 0; return result - res_start; diff --git a/scripts/mysqld_multi.sh b/scripts/mysqld_multi.sh index 2c3578834eb..0b33f61710e 100644 --- a/scripts/mysqld_multi.sh +++ b/scripts/mysqld_multi.sh @@ -308,9 +308,7 @@ sub report_mysqlds sub start_mysqlds() { - my (@groups, $com, $tmp, $i, @options, $j, $mysqld_found, $suffix_found, $info_sent); - - $suffix_found= 0; + my (@groups, $com, $tmp, $i, @options, $j, $mysqld_found, $info_sent); if (!$opt_no_log) { @@ -349,10 +347,6 @@ sub start_mysqlds() $options[$j]= quote_shell_word($options[$j]); $tmp.= " $options[$j]"; } - elsif ("--defaults-group-suffix=" eq substr($options[$j], 0, 24)) - { - $suffix_found= 1; - } else { $options[$j]= quote_shell_word($options[$j]); @@ -369,12 +363,6 @@ sub start_mysqlds() $info_sent= 1; } - if (!$suffix_found) - { - $com.= " --defaults-group-suffix="; - $com.= substr($groups[$i],6); - } - $com.= $tmp; if ($opt_wsrep_new_cluster) { diff --git a/scripts/wsrep_sst_mariabackup.sh b/scripts/wsrep_sst_mariabackup.sh index 1991fe4dd8d..63ff5646535 100644 --- a/scripts/wsrep_sst_mariabackup.sh +++ b/scripts/wsrep_sst_mariabackup.sh @@ -712,7 +712,8 @@ INNODB_DATA_HOME_DIR=${INNODB_DATA_HOME_DIR:-""} if [ ! -z "$INNODB_DATA_HOME_DIR_ARG" ]; then INNODB_DATA_HOME_DIR=$INNODB_DATA_HOME_DIR_ARG fi -# if INNODB_DATA_HOME_DIR env. variable is not set, try to get it from my.cnf +# if no command line arg and INNODB_DATA_HOME_DIR environment variable +# is not set, try to get it from my.cnf: if [ -z "$INNODB_DATA_HOME_DIR" ]; then INNODB_DATA_HOME_DIR=$(parse_cnf mysqld$WSREP_SST_OPT_SUFFIX_VALUE innodb-data-home-dir '') fi @@ -951,17 +952,25 @@ then ib_home_dir=$INNODB_DATA_HOME_DIR - # Try to set ib_log_dir from the command line: - ib_log_dir=$INNODB_LOG_GROUP_HOME_ARG - if [ -z "$ib_log_dir" ]; then - ib_log_dir=$(parse_cnf mysqld$WSREP_SST_OPT_SUFFIX_VALUE innodb-log-group-home-dir "") + WSREP_LOG_DIR=${WSREP_LOG_DIR:-""} + # Try to set WSREP_LOG_DIR from the command line: + if [ ! -z "$INNODB_LOG_GROUP_HOME_ARG" ]; then + WSREP_LOG_DIR=$INNODB_LOG_GROUP_HOME_ARG fi - if [ -z "$ib_log_dir" ]; then - ib_log_dir=$(parse_cnf --mysqld innodb-log-group-home-dir "") + # if no command line arg and WSREP_LOG_DIR is not set, + # try to get it from my.cnf: + if [ -z "$WSREP_LOG_DIR" ]; then + WSREP_LOG_DIR=$(parse_cnf mysqld$WSREP_SST_OPT_SUFFIX_VALUE innodb-log-group-home-dir '') fi + if [ -z "$WSREP_LOG_DIR" ]; then + WSREP_LOG_DIR=$(parse_cnf --mysqld innodb-log-group-home-dir '') + fi + + ib_log_dir=$WSREP_LOG_DIR # Try to set ib_undo_dir from the command line: - ib_undo_dir=$INNODB_UNDO_DIR_ARG + ib_undo_dir=${INNODB_UNDO_DIR_ARG:-""} + # if no command line arg then try to get it from my.cnf: if [ -z "$ib_undo_dir" ]; then ib_undo_dir=$(parse_cnf mysqld$WSREP_SST_OPT_SUFFIX_VALUE innodb-undo-directory "") fi diff --git a/scripts/wsrep_sst_rsync.sh b/scripts/wsrep_sst_rsync.sh index 96e542ce844..d42cf014009 100644 --- a/scripts/wsrep_sst_rsync.sh +++ b/scripts/wsrep_sst_rsync.sh @@ -152,10 +152,11 @@ fi WSREP_LOG_DIR=${WSREP_LOG_DIR:-""} # Try to set WSREP_LOG_DIR from the command line: -if [ -z "$WSREP_LOG_DIR" ]; then +if [ ! -z "$INNODB_LOG_GROUP_HOME_ARG" ]; then WSREP_LOG_DIR=$INNODB_LOG_GROUP_HOME_ARG fi -# if WSREP_LOG_DIR env. variable is not set, try to get it from my.cnf +# if no command line arg and WSREP_LOG_DIR is not set, +# try to get it from my.cnf: if [ -z "$WSREP_LOG_DIR" ]; then WSREP_LOG_DIR=$(parse_cnf mysqld$WSREP_SST_OPT_SUFFIX_VALUE innodb-log-group-home-dir '') fi @@ -176,7 +177,8 @@ INNODB_DATA_HOME_DIR=${INNODB_DATA_HOME_DIR:-""} if [ ! -z "$INNODB_DATA_HOME_DIR_ARG" ]; then INNODB_DATA_HOME_DIR=$INNODB_DATA_HOME_DIR_ARG fi -# if INNODB_DATA_HOME_DIR env. variable is not set, try to get it from my.cnf +# if no command line arg and INNODB_DATA_HOME_DIR environment variable +# is not set, try to get it from my.cnf: if [ -z "$INNODB_DATA_HOME_DIR" ]; then INNODB_DATA_HOME_DIR=$(parse_cnf mysqld$WSREP_SST_OPT_SUFFIX_VALUE innodb-data-home-dir '') fi diff --git a/sql/backup.cc b/sql/backup.cc index 5976506cf92..813485ea29a 100644 --- a/sql/backup.cc +++ b/sql/backup.cc @@ -1,4 +1,4 @@ -/* Copyright (c) 2018, MariaDB Corporation +/* Copyright (c) 2018, 2020, MariaDB Corporation. This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; version 2 of the License. @@ -96,7 +96,7 @@ bool run_backup_stage(THD *thd, backup_stages stage) do { - bool res; + bool res= false; backup_stages previous_stage= thd->current_backup_stage; thd->current_backup_stage= next_stage; switch (next_stage) { @@ -120,7 +120,6 @@ bool run_backup_stage(THD *thd, backup_stages stage) break; case BACKUP_FINISHED: DBUG_ASSERT(0); - res= 0; } if (res) { diff --git a/sql/ha_partition.cc b/sql/ha_partition.cc index b767045fa26..f745acda75f 100644 --- a/sql/ha_partition.cc +++ b/sql/ha_partition.cc @@ -9593,7 +9593,6 @@ double ha_partition::read_time(uint index, uint ranges, ha_rows rows) ha_rows ha_partition::records() { - int error; ha_rows tot_rows= 0; uint i; DBUG_ENTER("ha_partition::records"); @@ -9602,9 +9601,10 @@ ha_rows ha_partition::records() i < m_tot_parts; i= bitmap_get_next_set(&m_part_info->read_partitions, i)) { - ha_rows rows; - if (unlikely((error= m_file[i]->pre_records()) || - (rows= m_file[i]->records()) == HA_POS_ERROR)) + if (unlikely(m_file[i]->pre_records())) + DBUG_RETURN(HA_POS_ERROR); + const ha_rows rows= m_file[i]->records(); + if (unlikely(rows == HA_POS_ERROR)) DBUG_RETURN(HA_POS_ERROR); tot_rows+= rows; } diff --git a/sql/item.cc b/sql/item.cc index 61651323626..f8c29c8974c 100644 --- a/sql/item.cc +++ b/sql/item.cc @@ -7475,7 +7475,6 @@ Item *find_producing_item(Item *item, st_select_lex *sel) DBUG_ASSERT(item->type() == Item::FIELD_ITEM || (item->type() == Item::REF_ITEM && ((Item_ref *) item)->ref_type() == Item_ref::VIEW_REF)); - Item *producing_item; Item_field *field_item= NULL; Item_equal *item_equal= item->get_item_equal(); table_map tab_map= sel->master_unit()->derived->table->map; @@ -7497,6 +7496,7 @@ Item *find_producing_item(Item *item, st_select_lex *sel) List_iterator_fast<Item> li(sel->item_list); if (field_item) { + Item *producing_item= NULL; uint field_no= field_item->field->field_index; for (uint i= 0; i <= field_no; i++) producing_item= li++; diff --git a/sql/item_geofunc.cc b/sql/item_geofunc.cc index 9e6c8ea9008..ce52c6d246d 100644 --- a/sql/item_geofunc.cc +++ b/sql/item_geofunc.cc @@ -2380,12 +2380,15 @@ double Item_func_distance::val_real() MBR mbr1, mbr2; const char *c_end; - - if ((null_value= (args[0]->null_value || args[1]->null_value || - !(g1= Geometry::construct(&buffer1, res1->ptr(), res1->length())) || - !(g2= Geometry::construct(&buffer2, res2->ptr(), res2->length())) || - g1->get_mbr(&mbr1, &c_end) || - g2->get_mbr(&mbr2, &c_end)))) + if (args[0]->null_value || args[1]->null_value) + goto mem_error; + g1= Geometry::construct(&buffer1, res1->ptr(), res1->length()); + if (!g1) + goto mem_error; + g2= Geometry::construct(&buffer2, res2->ptr(), res2->length()); + if (!g2) + goto mem_error; + if (g1->get_mbr(&mbr1, &c_end) || g2->get_mbr(&mbr2, &c_end)) goto mem_error; mbr1.add_mbr(&mbr2); @@ -2534,7 +2537,7 @@ String *Item_func_pointonsurface::val_str(String *str) Geometry *g; MBR mbr; const char *c_end; - double UNINIT_VAR(px), UNINIT_VAR(py), x0, y0; + double UNINIT_VAR(px), UNINIT_VAR(py), x0, UNINIT_VAR(y0); String *result= 0; const Gcalc_scan_iterator::point *pprev= NULL; uint32 srid; diff --git a/sql/item_strfunc.cc b/sql/item_strfunc.cc index a61de0dfdaf..c735f697986 100644 --- a/sql/item_strfunc.cc +++ b/sql/item_strfunc.cc @@ -1,6 +1,6 @@ /* Copyright (c) 2000, 2017, Oracle and/or its affiliates. - Copyright (c) 2009, 2019, MariaDB Corporation + Copyright (c) 2009, 2020, MariaDB Corporation. This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by @@ -646,7 +646,7 @@ String *Item_func_concat_operator_oracle::val_str(String *str) { DBUG_ASSERT(fixed == 1); THD *thd= current_thd; - String *res; + String *res= NULL; uint i; null_value=0; @@ -656,7 +656,7 @@ String *Item_func_concat_operator_oracle::val_str(String *str) if ((res= args[i]->val_str(str))) break; } - if (i == arg_count) + if (!res) goto null; if (res != str) diff --git a/sql/sql_repl.cc b/sql/sql_repl.cc index 1080018b84d..d1c122ba7a5 100644 --- a/sql/sql_repl.cc +++ b/sql/sql_repl.cc @@ -375,11 +375,15 @@ static int send_file(THD *thd) We need net_flush here because the client will not know it needs to send us the file name until it has processed the load event entry */ - if (unlikely(net_flush(net) || (packet_len = my_net_read(net)) == packet_error)) + if (unlikely(net_flush(net))) { + read_error: errmsg = "while reading file name"; goto err; } + packet_len= my_net_read(net); + if (unlikely(packet_len == packet_error)) + goto read_error; // terminate with \0 for fn_format *((char*)net->read_pos + packet_len) = 0; diff --git a/sql/sql_yacc.yy b/sql/sql_yacc.yy index 3adc2801270..14b7a5589e1 100644 --- a/sql/sql_yacc.yy +++ b/sql/sql_yacc.yy @@ -4394,9 +4394,11 @@ sp_fetch_list: LEX *lex= Lex; sp_head *sp= lex->sphead; sp_pcontext *spc= lex->spcont; - sp_variable *spv; + sp_variable *spv= likely(spc != NULL) + ? spc->find_variable(&$1, false) + : NULL; - if (unlikely(!spc || !(spv = spc->find_variable(&$1, false)))) + if (unlikely(!spv)) my_yyabort_error((ER_SP_UNDECLARED_VAR, MYF(0), $1.str)); /* An SP local variable */ @@ -4408,9 +4410,11 @@ sp_fetch_list: LEX *lex= Lex; sp_head *sp= lex->sphead; sp_pcontext *spc= lex->spcont; - sp_variable *spv; + sp_variable *spv= likely(spc != NULL) + ? spc->find_variable(&$3, false) + : NULL; - if (unlikely(!spc || !(spv = spc->find_variable(&$3, false)))) + if (unlikely(!spv)) my_yyabort_error((ER_SP_UNDECLARED_VAR, MYF(0), $3.str)); /* An SP local variable */ diff --git a/sql/sql_yacc_ora.yy b/sql/sql_yacc_ora.yy index fdb3e90a509..9366a7bcd9f 100644 --- a/sql/sql_yacc_ora.yy +++ b/sql/sql_yacc_ora.yy @@ -4310,9 +4310,10 @@ sp_fetch_list: LEX *lex= Lex; sp_head *sp= lex->sphead; sp_pcontext *spc= lex->spcont; - sp_variable *spv; - - if (unlikely(!spc || !(spv = spc->find_variable(&$1, false)))) + sp_variable *spv= likely(spc != NULL) + ? spc->find_variable(&$1, false) + : NULL; + if (unlikely(!spv)) my_yyabort_error((ER_SP_UNDECLARED_VAR, MYF(0), $1.str)); /* An SP local variable */ @@ -4324,9 +4325,10 @@ sp_fetch_list: LEX *lex= Lex; sp_head *sp= lex->sphead; sp_pcontext *spc= lex->spcont; - sp_variable *spv; - - if (unlikely(!spc || !(spv = spc->find_variable(&$3, false)))) + sp_variable *spv= likely(spc != NULL) + ? spc->find_variable(&$3, false) + : NULL; + if (unlikely(!spv)) my_yyabort_error((ER_SP_UNDECLARED_VAR, MYF(0), $3.str)); /* An SP local variable */ diff --git a/sql/threadpool_generic.cc b/sql/threadpool_generic.cc index 6d6b22d5900..3f4997b8238 100644 --- a/sql/threadpool_generic.cc +++ b/sql/threadpool_generic.cc @@ -1079,7 +1079,10 @@ void thread_group_destroy(thread_group_t *thread_group) #endif if (!--shutdown_group_count) + { my_free(all_groups); + all_groups= 0; + } } /** @@ -1675,6 +1678,14 @@ TP_pool_generic::~TP_pool_generic() { thread_group_close(&all_groups[i]); } + + /* + Wait until memory occupied by all_groups is freed. + */ + int timeout_ms=5000; + while(all_groups && timeout_ms--) + my_sleep(1000); + threadpool_started= false; DBUG_VOID_RETURN; } diff --git a/storage/innobase/btr/btr0cur.cc b/storage/innobase/btr/btr0cur.cc index 5696d184386..0dae73c56d7 100644 --- a/storage/innobase/btr/btr0cur.cc +++ b/storage/innobase/btr/btr0cur.cc @@ -3510,17 +3510,23 @@ fail_err: } ulint max_size = page_get_max_insert_size_after_reorganize(page, 1); + if (max_size < rec_size) { + goto fail; + } + + const ulint n_recs = page_get_n_recs(page); + if (UNIV_UNLIKELY(n_recs >= 8189)) { + ut_ad(srv_page_size == 65536); + goto fail; + } if (page_has_garbage(page)) { - if ((max_size < rec_size - || max_size < BTR_CUR_PAGE_REORGANIZE_LIMIT) - && page_get_n_recs(page) > 1 + if (max_size < BTR_CUR_PAGE_REORGANIZE_LIMIT + && n_recs > 1 && page_get_max_insert_size(page, 1) < rec_size) { goto fail; } - } else if (max_size < rec_size) { - goto fail; } /* If there have been many consecutive inserts to the diff --git a/storage/innobase/buf/buf0rea.cc b/storage/innobase/buf/buf0rea.cc index ae9ecf7d81b..9bd1b16a0a2 100644 --- a/storage/innobase/buf/buf0rea.cc +++ b/storage/innobase/buf/buf0rea.cc @@ -265,24 +265,6 @@ buf_read_ahead_random(const page_id_t page_id, ulint zip_size, bool ibuf) * buf_read_ahead_random_area; if (fil_space_t* space = fil_space_acquire(page_id.space())) { -#ifdef UNIV_DEBUG - if (srv_file_per_table) { - ulint size = 0; - const ulint physical_size = space->physical_size(); - - for (const fil_node_t* node = - UT_LIST_GET_FIRST(space->chain); - node != NULL; - node = UT_LIST_GET_NEXT(chain, node)) { - - size += ulint(os_file_get_size(node->handle) - / physical_size); - } - - ut_ad(size == space->size); - } -#endif /* UNIV_DEBUG */ - high = space->max_page_number_for_io(high); space->release(); } else { diff --git a/storage/innobase/fil/fil0crypt.cc b/storage/innobase/fil/fil0crypt.cc index 7c4046871cc..7ae2f42ed57 100644 --- a/storage/innobase/fil/fil0crypt.cc +++ b/storage/innobase/fil/fil0crypt.cc @@ -1589,28 +1589,31 @@ inline fil_space_t *fil_system_t::keyrotate_next(fil_space_t *space, ut_ad(mutex_own(&mutex)); sized_ilist<fil_space_t, rotation_list_tag_t>::iterator it= - space ? space : rotation_list.begin(); + space && space->is_in_rotation_list ? space : rotation_list.begin(); const sized_ilist<fil_space_t, rotation_list_tag_t>::iterator end= rotation_list.end(); if (space) { - while (++it != end && (!UT_LIST_GET_LEN(it->chain) || it->is_stopping())); + const bool released= !space->release(); - /* If one of the encryption threads already started the encryption - of the table then don't remove the unencrypted spaces from rotation list - - If there is a change in innodb_encrypt_tables variables value then - don't remove the last processed tablespace from the rotation list. */ - space->release(); - - if (!space->referenced() && - (!recheck || space->crypt_data) && !encrypt == !srv_encrypt_tables && - space->is_in_rotation_list) + if (space->is_in_rotation_list) { - ut_a(!rotation_list.empty()); - rotation_list.remove(*space); - space->is_in_rotation_list= false; + while (++it != end && + (!UT_LIST_GET_LEN(it->chain) || it->is_stopping())); + + /* If one of the encryption threads already started the encryption + of the table then don't remove the unencrypted spaces from rotation list + + If there is a change in innodb_encrypt_tables variables value then + don't remove the last processed tablespace from the rotation list. */ + if (released && (!recheck || space->crypt_data) && + !encrypt == !srv_encrypt_tables) + { + ut_a(!rotation_list.empty()); + rotation_list.remove(*space); + space->is_in_rotation_list= false; + } } } diff --git a/storage/innobase/fil/fil0pagecompress.cc b/storage/innobase/fil/fil0pagecompress.cc index b3390a4cd12..1d38f9dc6b7 100644 --- a/storage/innobase/fil/fil0pagecompress.cc +++ b/storage/innobase/fil/fil0pagecompress.cc @@ -1,6 +1,6 @@ /***************************************************************************** -Copyright (C) 2013, 2019, MariaDB Corporation. +Copyright (C) 2013, 2020, MariaDB Corporation. This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software @@ -252,15 +252,6 @@ fail: memset(out_buf + tmp, 0, write_size - tmp); } -#ifdef UNIV_DEBUG - /* Verify that page can be decompressed */ - { - page_t tmp_buf[UNIV_PAGE_SIZE_MAX]; - page_t page[UNIV_PAGE_SIZE_MAX]; - memcpy(page, out_buf, write_size); - ut_ad(fil_page_decompress(tmp_buf, page, flags)); - } -#endif srv_stats.page_compression_saved.add(srv_page_size - write_size); srv_stats.pages_page_compressed.inc(); @@ -330,8 +321,6 @@ static ulint fil_page_compress_for_non_full_crc32( mach_write_to_2(out_buf + FIL_PAGE_DATA + FIL_PAGE_COMP_SIZE, write_size); -#ifdef UNIV_DEBUG - /* Verify */ ut_ad(fil_page_is_compressed(out_buf) || fil_page_is_compressed_encrypted(out_buf)); @@ -341,6 +330,7 @@ static ulint fil_page_compress_for_non_full_crc32( ut_ad(mach_read_from_2(out_buf + FIL_PAGE_DATA + FIL_PAGE_COMP_SIZE) == write_size); +#ifdef UNIV_DEBUG bool is_compressed = (mach_read_from_8(out_buf + FIL_PAGE_COMP_ALGO) == (ulint) comp_algo); @@ -348,19 +338,10 @@ static ulint fil_page_compress_for_non_full_crc32( (mach_read_from_2(out_buf + FIL_PAGE_DATA + FIL_PAGE_ENCRYPT_COMP_ALGO) == (ulint) comp_algo); +#endif /* UNIV_DEBUG */ ut_ad(is_compressed || is_encrypted_compressed); - /* Verify that page can be decompressed */ - { - page_t tmp_buf[UNIV_PAGE_SIZE_MAX]; - page_t page[UNIV_PAGE_SIZE_MAX]; - memcpy(page, out_buf, srv_page_size); - ut_ad(fil_page_decompress(tmp_buf, page, flags)); - ut_ad(!buf_page_is_corrupted(false, page, flags)); - } -#endif /* UNIV_DEBUG */ - write_size+=header_len; if (block_size <= 0) { diff --git a/storage/innobase/fts/fts0que.cc b/storage/innobase/fts/fts0que.cc index de592e7fb7f..9a4e7c1f486 100644 --- a/storage/innobase/fts/fts0que.cc +++ b/storage/innobase/fts/fts0que.cc @@ -2742,7 +2742,7 @@ fts_query_phrase_search( /* Ignore empty strings. */ if (num_token > 0) { - fts_string_t* token; + fts_string_t* token = NULL; fts_fetch_t fetch; trx_t* trx = query->trx; fts_ast_oper_t oper = query->oper; diff --git a/storage/innobase/handler/ha_innodb.cc b/storage/innobase/handler/ha_innodb.cc index 3e4da9bb8b2..38429878b65 100644 --- a/storage/innobase/handler/ha_innodb.cc +++ b/storage/innobase/handler/ha_innodb.cc @@ -19837,7 +19837,7 @@ static TYPELIB page_compression_algorithms_typelib= }; static MYSQL_SYSVAR_ENUM(compression_algorithm, innodb_compression_algorithm, PLUGIN_VAR_OPCMDARG, - "Compression algorithm used on page compression. One of: none, zlib, lz4, lzo, lzma, or bzip2", + "Compression algorithm used on page compression. One of: none, zlib, lz4, lzo, lzma, bzip2, or snappy", innodb_compression_algorithm_validate, NULL, /* We use here the largest number of supported compression method to enable all those methods that are available. Availability of compression diff --git a/storage/innobase/handler/handler0alter.cc b/storage/innobase/handler/handler0alter.cc index d8694da02d7..df42f20c55d 100644 --- a/storage/innobase/handler/handler0alter.cc +++ b/storage/innobase/handler/handler0alter.cc @@ -4758,7 +4758,11 @@ innobase_pk_order_preserved( if (old_pk_column) { new_field_order = lint(old_field); } else if (innobase_pk_col_is_existing(new_col_no, col_map, - old_n_cols)) { + old_n_cols) + || new_clust_index->table->persistent_autoinc + == new_field + 1) { + /* Adding an existing column or an AUTO_INCREMENT + column may change the existing ordering. */ new_field_order = lint(old_n_uniq + existing_field_count++); } else { @@ -6919,12 +6923,6 @@ error_handling_drop_uncached_1: user_table); dict_index_t* new_clust_index = dict_table_get_first_index( ctx->new_table); - ctx->skip_pk_sort = innobase_pk_order_preserved( - ctx->col_map, clust_index, new_clust_index); - - DBUG_EXECUTE_IF("innodb_alter_table_pk_assert_no_sort", - DBUG_ASSERT(ctx->skip_pk_sort);); - ut_ad(!new_clust_index->is_instant()); /* row_merge_build_index() depends on the correct value */ ut_ad(new_clust_index->n_core_null_bytes @@ -6947,6 +6945,12 @@ error_handling_drop_uncached_1: } } + ctx->skip_pk_sort = innobase_pk_order_preserved( + ctx->col_map, clust_index, new_clust_index); + + DBUG_EXECUTE_IF("innodb_alter_table_pk_assert_no_sort", + DBUG_ASSERT(ctx->skip_pk_sort);); + if (ctx->online) { /* Allocate a log for online table rebuild. */ rw_lock_x_lock(&clust_index->lock); diff --git a/storage/innobase/include/fil0fil.h b/storage/innobase/include/fil0fil.h index 2cbf233a4cb..6c86deeec59 100644 --- a/storage/innobase/include/fil0fil.h +++ b/storage/innobase/include/fil0fil.h @@ -272,8 +272,9 @@ struct fil_space_t /** Acquire a tablespace reference. */ void acquire() { n_pending_ops++; } - /** Release a tablespace reference. */ - void release() { ut_ad(referenced()); n_pending_ops--; } + /** Release a tablespace reference. + @return whether this was the last reference */ + bool release() { auto n= n_pending_ops--; ut_ad(n); return n == 1; } /** @return whether references are being held */ bool referenced() const { return n_pending_ops; } diff --git a/storage/innobase/include/page0page.h b/storage/innobase/include/page0page.h index 0de7f50f8c2..5c3ed18a4a5 100644 --- a/storage/innobase/include/page0page.h +++ b/storage/innobase/include/page0page.h @@ -949,20 +949,6 @@ page_mem_alloc_free( free record list */ ulint need); /*!< in: number of bytes allocated */ /************************************************************//** -Allocates a block of memory from the heap of an index page. -@return pointer to start of allocated buffer, or NULL if allocation fails */ -byte* -page_mem_alloc_heap( -/*================*/ - page_t* page, /*!< in/out: index page */ - page_zip_des_t* page_zip,/*!< in/out: compressed page with enough - space available for inserting the record, - or NULL */ - ulint need, /*!< in: total number of bytes needed */ - ulint* heap_no);/*!< out: this contains the heap number - of the allocated record - if allocation succeeds */ -/************************************************************//** Puts a record to free list. */ UNIV_INLINE void diff --git a/storage/innobase/page/page0cur.cc b/storage/innobase/page/page0cur.cc index c984d60a419..0586d6d8a33 100644 --- a/storage/innobase/page/page0cur.cc +++ b/storage/innobase/page/page0cur.cc @@ -1207,6 +1207,52 @@ page_direction_increment( 1U + page_header_get_field(page, PAGE_N_DIRECTION)); } +/************************************************************//** +Allocates a block of memory from the heap of an index page. +@return pointer to start of allocated buffer, or NULL if allocation fails */ +static +byte* +page_mem_alloc_heap( +/*================*/ + page_t* page, /*!< in/out: index page */ + page_zip_des_t* page_zip,/*!< in/out: compressed page with enough + space available for inserting the record, + or NULL */ + ulint need, /*!< in: total number of bytes needed */ + ulint* heap_no)/*!< out: this contains the heap number + of the allocated record + if allocation succeeds */ +{ + byte* block; + ulint avl_space; + + ut_ad(page && heap_no); + + avl_space = page_get_max_insert_size(page, 1); + + if (avl_space >= need) { + const ulint h = page_dir_get_n_heap(page); + if (UNIV_UNLIKELY(h >= 8191)) { + /* At the minimum record size of 5+2 bytes, + we can only reach this condition when using + innodb_page_size=64k. */ + ut_ad(srv_page_size == 65536); + return(NULL); + } + *heap_no = h; + + block = page_header_get_ptr(page, PAGE_HEAP_TOP); + + page_header_set_ptr(page, page_zip, PAGE_HEAP_TOP, + block + need); + page_dir_set_n_heap(page, page_zip, 1 + *heap_no); + + return(block); + } + + return(NULL); +} + /***********************************************************//** Inserts a record next to page cursor on an uncompressed page. Returns pointer to inserted record if succeed, i.e., enough diff --git a/storage/innobase/page/page0page.cc b/storage/innobase/page/page0page.cc index 2c8754a3685..86c86bd084d 100644 --- a/storage/innobase/page/page0page.cc +++ b/storage/innobase/page/page0page.cc @@ -251,43 +251,6 @@ page_set_autoinc( } } -/************************************************************//** -Allocates a block of memory from the heap of an index page. -@return pointer to start of allocated buffer, or NULL if allocation fails */ -byte* -page_mem_alloc_heap( -/*================*/ - page_t* page, /*!< in/out: index page */ - page_zip_des_t* page_zip,/*!< in/out: compressed page with enough - space available for inserting the record, - or NULL */ - ulint need, /*!< in: total number of bytes needed */ - ulint* heap_no)/*!< out: this contains the heap number - of the allocated record - if allocation succeeds */ -{ - byte* block; - ulint avl_space; - - ut_ad(page && heap_no); - - avl_space = page_get_max_insert_size(page, 1); - - if (avl_space >= need) { - block = page_header_get_ptr(page, PAGE_HEAP_TOP); - - page_header_set_ptr(page, page_zip, PAGE_HEAP_TOP, - block + need); - *heap_no = page_dir_get_n_heap(page); - - page_dir_set_n_heap(page, page_zip, 1 + *heap_no); - - return(block); - } - - return(NULL); -} - /**********************************************************//** Writes a log record of page creation. */ UNIV_INLINE diff --git a/storage/maria/ma_create.c b/storage/maria/ma_create.c index 93d65bf3a7d..b94f503641a 100644 --- a/storage/maria/ma_create.c +++ b/storage/maria/ma_create.c @@ -75,7 +75,7 @@ int maria_create(const char *name, enum data_file_type datafile_type, uint max_field_lengths, extra_header_size, column_nr; uint internal_table= flags & HA_CREATE_INTERNAL_TABLE; ulong reclength, real_reclength,min_pack_length; - char kfilename[FN_REFLEN], klinkname[FN_REFLEN], *klinkname_ptr; + char kfilename[FN_REFLEN], klinkname[FN_REFLEN], *klinkname_ptr= NullS; char dfilename[FN_REFLEN], dlinkname[FN_REFLEN], *dlinkname_ptr= 0; ulong pack_reclength; ulonglong tot_length,max_rows, tmp; @@ -894,7 +894,6 @@ int maria_create(const char *name, enum data_file_type datafile_type, fn_format(kfilename, name, "", MARIA_NAME_IEXT, MY_UNPACK_FILENAME | MY_RETURN_REAL_PATH | (have_iext ? MY_REPLACE_EXT : MY_APPEND_EXT)); - klinkname_ptr= NullS; /* Replace the current file. Don't sync dir now if the data file has the same path. diff --git a/storage/maria/ma_loghandler.c b/storage/maria/ma_loghandler.c index d943666065a..42755a63a03 100644 --- a/storage/maria/ma_loghandler.c +++ b/storage/maria/ma_loghandler.c @@ -3618,7 +3618,8 @@ my_bool translog_init_with_table(const char *directory, int old_log_was_recovered= 0, logs_found= 0; uint old_flags= flags; uint32 start_file_num= 1; - TRANSLOG_ADDRESS sure_page, last_page, last_valid_page, checkpoint_lsn; + TRANSLOG_ADDRESS UNINIT_VAR(sure_page), last_page, last_valid_page, + checkpoint_lsn; my_bool version_changed= 0; DBUG_ENTER("translog_init_with_table"); diff --git a/storage/myisam/mi_create.c b/storage/myisam/mi_create.c index fd230698acc..9f17a9b2de9 100644 --- a/storage/myisam/mi_create.c +++ b/storage/myisam/mi_create.c @@ -46,7 +46,7 @@ int mi_create(const char *name,uint keys,MI_KEYDEF *keydefs, uint aligned_key_start, block_length, res; uint internal_table= flags & HA_CREATE_INTERNAL_TABLE; ulong reclength, real_reclength,min_pack_length; - char kfilename[FN_REFLEN],klinkname[FN_REFLEN], *klinkname_ptr; + char kfilename[FN_REFLEN],klinkname[FN_REFLEN], *klinkname_ptr= 0; char dfilename[FN_REFLEN],dlinkname[FN_REFLEN], *dlinkname_ptr= 0; ulong pack_reclength; ulonglong tot_length,max_rows, tmp; @@ -622,7 +622,6 @@ int mi_create(const char *name,uint keys,MI_KEYDEF *keydefs, fn_format(kfilename, name, "", MI_NAME_IEXT, MY_UNPACK_FILENAME | MY_RETURN_REAL_PATH | (have_iext ? MY_REPLACE_EXT : MY_APPEND_EXT)); - klinkname_ptr= 0; /* Replace the current file */ create_flag=(flags & HA_CREATE_KEEP_FILES) ? 0 : MY_DELETE_OLD; } diff --git a/strings/ctype-ucs2.c b/strings/ctype-ucs2.c index 71530b0a7c1..586289c51fd 100644 --- a/strings/ctype-ucs2.c +++ b/strings/ctype-ucs2.c @@ -829,7 +829,7 @@ my_strtoll10_mb2(CHARSET_INFO *cs __attribute__((unused)), const char *nptr, char **endptr, int *error) { const uchar *s, *end, *start, *n_end, *true_end; - uchar c; + uchar UNINIT_VAR(c); unsigned long i, j, k; ulonglong li; int negative; |