diff --git a/mysql-test/r/view.result b/mysql-test/r/view.result index a09856c77a4..721ad052935 100644 --- a/mysql-test/r/view.result +++ b/mysql-test/r/view.result @@ -6573,6 +6573,25 @@ Warnings: Warning 1356 View 'test.v' references invalid table(s) or column(s) or function(s) or definer/invoker of view lack rights to use them DROP VIEW v; # +# MDEV-13439: Database permissions are not enough to run a subquery +# with GROUP BY within a view +# +create database test_db; +use test_db; +create table t (i int); +create user foo@localhost; +grant all on test_db.* to foo@localhost; +connect con1,localhost,foo,,; +use test_db; +create view v as select * from (select i from t group by i) sq; +select * from v; +i +disconnect con1; +connection default; +use test; +drop database test_db; +drop user foo@localhost; +# # End of 10.2 tests # # diff --git a/mysql-test/suite/gcol/r/gcol_bugfixes.result b/mysql-test/suite/gcol/r/gcol_bugfixes.result index fd40515225e..9aff30aabc9 100644 --- a/mysql-test/suite/gcol/r/gcol_bugfixes.result +++ b/mysql-test/suite/gcol/r/gcol_bugfixes.result @@ -576,6 +576,19 @@ SELECT 1 FROM t WHERE c GROUP BY b; COMMIT; DROP TABLE t; # +# Bug #25793677 INNODB: FAILING ASSERTION: CLUST_TEMPL_FOR_SEC || LEN .... +# +CREATE TABLE v ( +a INT, +c INT, +b CHAR(2) GENERATED ALWAYS AS (a IN (1)) VIRTUAL, +KEY(c,b(1))) charset utf8mb4; +INSERT INTO v (a,c) VALUES (1,1); +SELECT (SELECT MAX(c) FROM v); +(SELECT MAX(c) FROM v) +1 +DROP TABLE v; +# # MDEV-9255 Add generation_expression to information_schema.columns. # CREATE TABLE gcol_t1 ( diff --git a/mysql-test/suite/gcol/t/gcol_bugfixes.test b/mysql-test/suite/gcol/t/gcol_bugfixes.test index 4acae77e830..5563347a02a 100644 --- a/mysql-test/suite/gcol/t/gcol_bugfixes.test +++ b/mysql-test/suite/gcol/t/gcol_bugfixes.test @@ -537,6 +537,19 @@ SELECT 1 FROM t WHERE c GROUP BY b; COMMIT; DROP TABLE t; +--echo # +--echo # Bug #25793677 INNODB: FAILING ASSERTION: CLUST_TEMPL_FOR_SEC || LEN .... +--echo # + +CREATE TABLE v ( +a INT, +c INT, +b CHAR(2) GENERATED ALWAYS AS (a IN (1)) VIRTUAL, +KEY(c,b(1))) charset utf8mb4; +INSERT INTO v (a,c) VALUES (1,1); +SELECT (SELECT MAX(c) FROM v); +DROP TABLE v; + --echo # --echo # MDEV-9255 Add generation_expression to information_schema.columns. --echo # diff --git a/mysql-test/suite/innodb/r/rename_table.result b/mysql-test/suite/innodb/r/rename_table.result new file mode 100644 index 00000000000..3d7c3ff1b0e --- /dev/null +++ b/mysql-test/suite/innodb/r/rename_table.result @@ -0,0 +1,20 @@ +CREATE DATABASE test_jfg; +CREATE DATABASE test_jfg2; +CREATE TABLE test_jfg.test (a int unsigned PRIMARY KEY) ENGINE=InnoDB; +RENAME TABLE test_jfg.test TO test_jfg2.test; +SELECT REPLACE(path,'\\','/') path +FROM INFORMATION_SCHEMA.INNODB_SYS_DATAFILES WHERE PATH LIKE '%test%'; +path +./test_jfg2/test.ibd +DROP DATABASE test_jfg; +DROP DATABASE test_jfg2; +CREATE DATABASE abc_def; +CREATE DATABASE abc_def2; +CREATE TABLE abc_def.test (a int unsigned PRIMARY KEY) ENGINE=InnoDB; +RENAME TABLE abc_def.test TO abc_def2.test1; +SELECT REPLACE(path,'\\','/') path +FROM INFORMATION_SCHEMA.INNODB_SYS_DATAFILES WHERE PATH LIKE '%test%'; +path +./abc_def2/test1.ibd +DROP DATABASE abc_def; +DROP DATABASE abc_def2; diff --git a/mysql-test/suite/innodb/t/rename_table.opt b/mysql-test/suite/innodb/t/rename_table.opt new file mode 100644 index 00000000000..a4c52ea7d79 --- /dev/null +++ b/mysql-test/suite/innodb/t/rename_table.opt @@ -0,0 +1,2 @@ +--innodb +--innodb-sys-datafiles diff --git a/mysql-test/suite/innodb/t/rename_table.test b/mysql-test/suite/innodb/t/rename_table.test new file mode 100644 index 00000000000..ea9f70bacb0 --- /dev/null +++ b/mysql-test/suite/innodb/t/rename_table.test @@ -0,0 +1,31 @@ +--source include/have_innodb.inc +--source include/not_embedded.inc + +CREATE DATABASE test_jfg; +CREATE DATABASE test_jfg2; +CREATE TABLE test_jfg.test (a int unsigned PRIMARY KEY) ENGINE=InnoDB; +RENAME TABLE test_jfg.test TO test_jfg2.test; + +SELECT REPLACE(path,'\\','/') path +FROM INFORMATION_SCHEMA.INNODB_SYS_DATAFILES WHERE PATH LIKE '%test%'; + +DROP DATABASE test_jfg; + +--source include/restart_mysqld.inc + +DROP DATABASE test_jfg2; + +CREATE DATABASE abc_def; +CREATE DATABASE abc_def2; + +CREATE TABLE abc_def.test (a int unsigned PRIMARY KEY) ENGINE=InnoDB; +RENAME TABLE abc_def.test TO abc_def2.test1; + +SELECT REPLACE(path,'\\','/') path +FROM INFORMATION_SCHEMA.INNODB_SYS_DATAFILES WHERE PATH LIKE '%test%'; + +DROP DATABASE abc_def; + +--source include/restart_mysqld.inc + +DROP DATABASE abc_def2; diff --git a/mysql-test/suite/sys_vars/r/sysvars_innodb.result b/mysql-test/suite/sys_vars/r/sysvars_innodb.result index 7402b84dc96..62a72525aab 100644 --- a/mysql-test/suite/sys_vars/r/sysvars_innodb.result +++ b/mysql-test/suite/sys_vars/r/sysvars_innodb.result @@ -3074,7 +3074,7 @@ READ_ONLY NO COMMAND_LINE_ARGUMENT OPTIONAL VARIABLE_NAME INNODB_VERSION SESSION_VALUE NULL -GLOBAL_VALUE 5.7.18 +GLOBAL_VALUE 5.7.19 GLOBAL_VALUE_ORIGIN COMPILE-TIME DEFAULT_VALUE NULL VARIABLE_SCOPE GLOBAL diff --git a/mysql-test/t/view.test b/mysql-test/t/view.test index 00a040ccfdc..a9d6d9cec9c 100644 --- a/mysql-test/t/view.test +++ b/mysql-test/t/view.test @@ -6274,6 +6274,31 @@ DROP TABLE IF EXISTS t; SHOW CREATE VIEW v; DROP VIEW v; +--echo # +--echo # MDEV-13439: Database permissions are not enough to run a subquery +--echo # with GROUP BY within a view +--echo # + +create database test_db; +use test_db; +create table t (i int); + +create user foo@localhost; +grant all on test_db.* to foo@localhost; + +--connect (con1,localhost,foo,,) + +use test_db; +create view v as select * from (select i from t group by i) sq; +select * from v; + +# Cleanup +--disconnect con1 +--connection default +use test; +drop database test_db; +drop user foo@localhost; + --echo # --echo # End of 10.2 tests --echo # diff --git a/scripts/wsrep_sst_mysqldump.sh b/scripts/wsrep_sst_mysqldump.sh index 5f25c2c9d13..aaa82e1ed5c 100644 --- a/scripts/wsrep_sst_mysqldump.sh +++ b/scripts/wsrep_sst_mysqldump.sh @@ -56,7 +56,7 @@ then fi # Check client version -if ! $MYSQL_CLIENT --version | grep 'Distrib 10.1' >/dev/null +if ! $MYSQL_CLIENT --version | grep 'Distrib 10.' >/dev/null then $MYSQL_CLIENT --version >&2 wsrep_log_error "this operation requires MySQL client version 10 or newer" @@ -133,7 +133,7 @@ SET_GTID_BINLOG_STATE="" SQL_LOG_BIN_OFF="" # Safety check -if echo $SERVER_VERSION | grep '^10.1' > /dev/null +if echo $SERVER_VERSION | grep '^10.' > /dev/null then # If binary logging is enabled on the joiner node, we need to copy donor's # gtid_binlog_state to joiner. In order to do that, a RESET MASTER must be diff --git a/sql/item_cmpfunc.cc b/sql/item_cmpfunc.cc index 4bcb7397e52..fc076b766c2 100644 --- a/sql/item_cmpfunc.cc +++ b/sql/item_cmpfunc.cc @@ -550,14 +550,14 @@ bool Arg_comparator::set_cmp_func_string() { func= is_owner_equal_func() ? &Arg_comparator::compare_e_json_str: &Arg_comparator::compare_json_str; - return false; + return 0; } else if ((*b)->type() == Item::FUNC_ITEM && ((Item_func *) (*b))->functype() == Item_func::JSON_EXTRACT_FUNC) { func= is_owner_equal_func() ? &Arg_comparator::compare_e_json_str: &Arg_comparator::compare_str_json; - return false; + return 0; } } @@ -650,7 +650,6 @@ bool Arg_comparator::set_cmp_func_real() return false; } - bool Arg_comparator::set_cmp_func_decimal() { THD *thd= current_thd; diff --git a/sql/sql_acl.cc b/sql/sql_acl.cc index f82c68e1889..41d0e73a84e 100644 --- a/sql/sql_acl.cc +++ b/sql/sql_acl.cc @@ -7630,8 +7630,11 @@ bool check_grant(THD *thd, ulong want_access, TABLE_LIST *tables, /* It is subquery in the FROM clause. VIEW set t_ref->derived after table opening, but this function always called before table opening. + + NOTE: is_derived() can't be used here because subquery in this case + the FROM clase (derived tables) can be not be marked yet. */ - if (!t_ref->referencing_view) + if (t_ref->is_anonymous_derived_table() || t_ref->schema_table) { /* If it's a temporary table created for a subquery in the FROM diff --git a/sql/sql_cache.cc b/sql/sql_cache.cc index 89afef4eaf7..96a64697390 100644 --- a/sql/sql_cache.cc +++ b/sql/sql_cache.cc @@ -1413,6 +1413,8 @@ void Query_cache::store_query(THD *thd, TABLE_LIST *tables_used) flags.client_long_flag= MY_TEST(thd->client_capabilities & CLIENT_LONG_FLAG); flags.client_protocol_41= MY_TEST(thd->client_capabilities & CLIENT_PROTOCOL_41); + flags.client_depr_eof= MY_TEST(thd->client_capabilities & + CLIENT_DEPRECATE_EOF); /* Protocol influences result format, so statement results in the binary protocol (COM_EXECUTE) cannot be served to statements asking for results @@ -1443,12 +1445,13 @@ void Query_cache::store_query(THD *thd, TABLE_LIST *tables_used) flags.div_precision_increment= thd->variables.div_precincrement; flags.default_week_format= thd->variables.default_week_format; DBUG_PRINT("qcache", ("\ -long %d, 4.1: %d, bin_proto: %d, more results %d, pkt_nr: %d, \ +long %d, 4.1: %d, eof: %d, bin_proto: %d, more results %d, pkt_nr: %d, \ CS client: %u, CS result: %u, CS conn: %u, limit: %lu, TZ: 0x%lx, \ sql mode: 0x%llx, sort len: %lu, conncat len: %lu, div_precision: %lu, \ def_week_frmt: %lu, in_trans: %d, autocommit: %d", (int)flags.client_long_flag, (int)flags.client_protocol_41, + (int)flags.client_depr_eof, (int)flags.protocol_type, (int)flags.more_results_exists, flags.pkt_nr, @@ -1917,6 +1920,8 @@ Query_cache::send_result_to_client(THD *thd, char *org_sql, uint query_length) flags.client_long_flag= MY_TEST(thd->client_capabilities & CLIENT_LONG_FLAG); flags.client_protocol_41= MY_TEST(thd->client_capabilities & CLIENT_PROTOCOL_41); + flags.client_depr_eof= MY_TEST(thd->client_capabilities & + CLIENT_DEPRECATE_EOF); flags.protocol_type= (unsigned int) thd->protocol->type(); flags.more_results_exists= MY_TEST(thd->server_status & SERVER_MORE_RESULTS_EXISTS); @@ -1938,12 +1943,13 @@ Query_cache::send_result_to_client(THD *thd, char *org_sql, uint query_length) flags.default_week_format= thd->variables.default_week_format; flags.lc_time_names= thd->variables.lc_time_names; DBUG_PRINT("qcache", ("\ -long %d, 4.1: %d, bin_proto: %d, more results %d, pkt_nr: %d, \ +long %d, 4.1: %d, eof: %d, bin_proto: %d, more results %d, pkt_nr: %d, \ CS client: %u, CS result: %u, CS conn: %u, limit: %lu, TZ: 0x%lx, \ sql mode: 0x%llx, sort len: %lu, conncat len: %lu, div_precision: %lu, \ def_week_frmt: %lu, in_trans: %d, autocommit: %d", (int)flags.client_long_flag, (int)flags.client_protocol_41, + (int)flags.client_depr_eof, (int)flags.protocol_type, (int)flags.more_results_exists, flags.pkt_nr, diff --git a/sql/sql_cache.h b/sql/sql_cache.h index 21f9c66dc4f..3230034cf74 100644 --- a/sql/sql_cache.h +++ b/sql/sql_cache.h @@ -545,6 +545,7 @@ struct Query_cache_query_flags { unsigned int client_long_flag:1; unsigned int client_protocol_41:1; + unsigned int client_depr_eof:1; unsigned int protocol_type:2; unsigned int more_results_exists:1; unsigned int in_trans:1; diff --git a/sql/sql_derived.cc b/sql/sql_derived.cc index 56909364f2a..c278c5d5aa9 100644 --- a/sql/sql_derived.cc +++ b/sql/sql_derived.cc @@ -823,13 +823,14 @@ exit: table->derived_select_number= first_select->select_number; table->s->tmp_table= INTERNAL_TMP_TABLE; #ifndef NO_EMBEDDED_ACCESS_CHECKS - if (derived->referencing_view) + if (derived->is_view()) table->grant= derived->grant; else { + DBUG_ASSERT(derived->is_derived()); + DBUG_ASSERT(derived->is_anonymous_derived_table()); table->grant.privilege= SELECT_ACL; - if (derived->is_derived()) - derived->grant.privilege= SELECT_ACL; + derived->grant.privilege= SELECT_ACL; } #endif /* Add new temporary table to list of open derived tables */ diff --git a/storage/innobase/buf/buf0buf.cc b/storage/innobase/buf/buf0buf.cc index d1476cca67f..b57fba75869 100644 --- a/storage/innobase/buf/buf0buf.cc +++ b/storage/innobase/buf/buf0buf.cc @@ -6038,7 +6038,7 @@ database_corrupted: && fil_page_get_type(frame) == FIL_PAGE_INDEX && page_is_leaf(frame)) { - if (bpage && bpage->encrypted) { + if (bpage->encrypted) { ib::warn() << "Table in tablespace " << bpage->id.space() diff --git a/storage/innobase/buf/buf0flu.cc b/storage/innobase/buf/buf0flu.cc index 2dcc5a9b9a9..8575de8bfa3 100644 --- a/storage/innobase/buf/buf0flu.cc +++ b/storage/innobase/buf/buf0flu.cc @@ -1884,8 +1884,6 @@ buf_flush_batch( buf_pool_mutex_enter(buf_pool); - ulint count __attribute__((unused))= 0; - /* Note: The buffer pool mutex is released and reacquired within the flush functions. */ switch (flush_type) { @@ -1902,8 +1900,7 @@ buf_flush_batch( buf_pool_mutex_exit(buf_pool); - DBUG_PRINT("ib_buf", ("flush %u completed, %u pages", - unsigned(flush_type), unsigned(count))); + DBUG_LOG("ib_buf", "flush " << flush_type << " completed"); } /******************************************************************//** diff --git a/storage/innobase/fil/fil0fil.cc b/storage/innobase/fil/fil0fil.cc index fec7405cb6d..1cafb253630 100644 --- a/storage/innobase/fil/fil0fil.cc +++ b/storage/innobase/fil/fil0fil.cc @@ -3292,15 +3292,17 @@ fil_prepare_for_truncate( /** Reinitialize the original tablespace header with the same space id for single tablespace -@param[in] id space id of the tablespace +@param[in] table table belongs to tablespace @param[in] size size in blocks @param[in] trx Transaction covering truncate */ void -fil_reinit_space_header( - ulint id, +fil_reinit_space_header_for_table( + dict_table_t* table, ulint size, trx_t* trx) { + ulint id = table->space; + ut_a(!is_system_tablespace(id)); /* Invalidate in the buffer pool all pages belonging @@ -3309,6 +3311,9 @@ fil_reinit_space_header( and the dict operation lock during the scan and aquire it again after the buffer pool scan.*/ + /* Release the lock on the indexes too. So that + they won't violate the latch ordering. */ + dict_table_x_unlock_indexes(table); row_mysql_unlock_data_dictionary(trx); /* Lock the search latch in shared mode to prevent user @@ -3317,8 +3322,11 @@ fil_reinit_space_header( DEBUG_SYNC_C("buffer_pool_scan"); buf_LRU_flush_or_remove_pages(id, BUF_REMOVE_ALL_NO_WRITE, 0); btr_search_s_unlock_all(); + row_mysql_lock_data_dictionary(trx); + dict_table_x_lock_indexes(table); + /* Remove all insert buffer entries for the tablespace */ ibuf_delete_for_discarded_space(id); @@ -4636,7 +4644,7 @@ fil_ibd_load( break; } - /* Fall through to error handling */ + /* fall through */ case DB_TABLESPACE_EXISTS: return(FIL_LOAD_INVALID); diff --git a/storage/innobase/handler/ha_innodb.cc b/storage/innobase/handler/ha_innodb.cc index e4f2de1adec..3ca915d5420 100644 --- a/storage/innobase/handler/ha_innodb.cc +++ b/storage/innobase/handler/ha_innodb.cc @@ -15648,10 +15648,14 @@ get_foreign_key_info( if (ref_table == NULL) { - ib::info() << "Foreign Key referenced table " - << foreign->referenced_table_name - << " not found for foreign table " - << foreign->foreign_table_name; + if (!thd_test_options( + thd, OPTION_NO_FOREIGN_KEY_CHECKS)) { + ib::info() + << "Foreign Key referenced table " + << foreign->referenced_table_name + << " not found for foreign table " + << foreign->foreign_table_name; + } } else { dict_table_close(ref_table, TRUE, FALSE); diff --git a/storage/innobase/include/fil0fil.h b/storage/innobase/include/fil0fil.h index 097be6a5f96..204f031bce2 100644 --- a/storage/innobase/include/fil0fil.h +++ b/storage/innobase/include/fil0fil.h @@ -963,12 +963,12 @@ fil_prepare_for_truncate( /** Reinitialize the original tablespace header with the same space id for single tablespace -@param[in] id space id of the tablespace +@param[in] table table belongs to the tablespace @param[in] size size in blocks @param[in] trx Transaction covering truncate */ void -fil_reinit_space_header( - ulint id, +fil_reinit_space_header_for_table( + dict_table_t* table, ulint size, trx_t* trx); diff --git a/storage/innobase/include/univ.i b/storage/innobase/include/univ.i index a5635fc4ecd..21ca95bacb7 100644 --- a/storage/innobase/include/univ.i +++ b/storage/innobase/include/univ.i @@ -41,7 +41,7 @@ Created 1/20/1994 Heikki Tuuri #define INNODB_VERSION_MAJOR 5 #define INNODB_VERSION_MINOR 7 -#define INNODB_VERSION_BUGFIX 18 +#define INNODB_VERSION_BUGFIX 19 /* The following is the InnoDB version as shown in SELECT plugin_version FROM information_schema.plugins; diff --git a/storage/innobase/include/ut0stage.h b/storage/innobase/include/ut0stage.h index a4ff0a1c874..1d5457a3ab0 100644 --- a/storage/innobase/include/ut0stage.h +++ b/storage/innobase/include/ut0stage.h @@ -267,12 +267,10 @@ ut_stage_alter_t::n_pk_recs_inc() } /** Flag either one record or one page processed, depending on the -current phase. -@param[in] inc_val flag this many units processed at once */ +current phase. */ inline void -ut_stage_alter_t::inc( - ulint inc_val __attribute__((unused)) /* = 1 */) +ut_stage_alter_t::inc(ulint) { if (m_progress == NULL) { return; @@ -286,12 +284,14 @@ ut_stage_alter_t::inc( ut_error; case READ_PK: m_n_pk_pages++; +#if 0 /* TODO: MySQL 5.7 PSI */ ut_ad(inc_val == 1); /* Overall the read pk phase will read all the pages from the PK and will do work, proportional to the number of added indexes, thus when this is called once per read page we increment with 1 + m_n_sort_indexes */ inc_val = 1 + m_n_sort_indexes; +#endif break; case SORT: multi_factor = m_sort_multi_factor; diff --git a/storage/innobase/lock/lock0lock.cc b/storage/innobase/lock/lock0lock.cc index a6caa009ef7..d6e8be7fac0 100644 --- a/storage/innobase/lock/lock0lock.cc +++ b/storage/innobase/lock/lock0lock.cc @@ -1853,6 +1853,7 @@ lock_rec_insert_by_trx_age( return DB_SUCCESS; } +#ifdef UNIV_DEBUG static bool lock_queue_validate( @@ -1888,6 +1889,7 @@ lock_queue_validate( } return true; } +#endif /* UNIV_DEBUG */ static void diff --git a/storage/innobase/row/row0log.cc b/storage/innobase/row/row0log.cc index 6df0d745e46..31a5402dc15 100644 --- a/storage/innobase/row/row0log.cc +++ b/storage/innobase/row/row0log.cc @@ -1,6 +1,6 @@ /***************************************************************************** -Copyright (c) 2011, 2016, Oracle and/or its affiliates. All Rights Reserved. +Copyright (c) 2011, 2017, Oracle and/or its affiliates. All Rights Reserved. Copyright (c) 2017, MariaDB Corporation. This program is free software; you can redistribute it and/or modify it under @@ -2419,6 +2419,9 @@ row_log_table_apply_op( next_mrec = mrec + rec_offs_data_size(offsets); if (log->table->n_v_cols) { + if (next_mrec + 2 > mrec_end) { + return(NULL); + } next_mrec += mach_read_from_2(next_mrec); } @@ -2457,7 +2460,7 @@ row_log_table_apply_op( rec_init_offsets_temp(mrec, new_index, offsets); next_mrec = mrec + rec_offs_data_size(offsets) + ext_size; if (log->table->n_v_cols) { - if (next_mrec + 2 >= mrec_end) { + if (next_mrec + 2 > mrec_end) { return(NULL); } diff --git a/storage/innobase/row/row0merge.cc b/storage/innobase/row/row0merge.cc index 73cb3fcea6f..de1f35a876e 100644 --- a/storage/innobase/row/row0merge.cc +++ b/storage/innobase/row/row0merge.cc @@ -1,6 +1,6 @@ /***************************************************************************** -Copyright (c) 2005, 2016, Oracle and/or its affiliates. All Rights Reserved. +Copyright (c) 2005, 2017, Oracle and/or its affiliates. All Rights Reserved. Copyright (c) 2014, 2017, MariaDB Corporation. This program is free software; you can redistribute it and/or modify it under @@ -1997,6 +1997,8 @@ row_merge_read_clustered_index( goto func_exit; } + mem_heap_empty(row_heap); + page_cur_move_to_next(cur); stage->n_pk_recs_inc(); @@ -2676,7 +2678,6 @@ write_buffers: goto func_exit; } - mem_heap_empty(row_heap); if (v_heap) { mem_heap_empty(v_heap); } diff --git a/storage/innobase/row/row0mysql.cc b/storage/innobase/row/row0mysql.cc index 3fe96aba0eb..c205d818802 100644 --- a/storage/innobase/row/row0mysql.cc +++ b/storage/innobase/row/row0mysql.cc @@ -4597,6 +4597,15 @@ row_rename_table_for_mysql( && dict_table_is_file_per_table(table)) { /* Make a new pathname to update SYS_DATAFILES. */ char* new_path = row_make_new_pathname(table, new_name); + char* old_path = fil_space_get_first_path(table->space); + + /* If old path and new path are the same means tablename + has not changed and only the database name holding the table + has changed so we need to make the complete filepath again. */ + if (!dict_tables_have_same_db(old_name, new_name)) { + ut_free(new_path); + new_path = fil_make_filepath(NULL, new_name, IBD, false); + } info = pars_info_create(); @@ -4616,6 +4625,7 @@ row_rename_table_for_mysql( "END;\n" , FALSE, trx); + ut_free(old_path); ut_free(new_path); } if (err != DB_SUCCESS) { diff --git a/storage/innobase/row/row0sel.cc b/storage/innobase/row/row0sel.cc index 03afd328eb5..b9ee44873ec 100644 --- a/storage/innobase/row/row0sel.cc +++ b/storage/innobase/row/row0sel.cc @@ -2981,8 +2981,6 @@ row_sel_field_store_in_mysql_format_func( @param[in] field_no templ->rec_field_no or templ->clust_rec_field_no or templ->icp_rec_field_no - or sec field no if clust_templ_for_sec - is TRUE @param[in] templ row template */ static MY_ATTRIBUTE((warn_unused_result)) @@ -3141,10 +3139,6 @@ be needed in the query. @param[in] rec_clust whether the rec in the clustered index @param[in] index index of rec @param[in] offsets array returned by rec_get_offsets(rec) -@param[in] clust_templ_for_sec TRUE if rec belongs to secondary index - but the prebuilt->template is in - clustered index format and it is - used only for end range comparison @return TRUE on success, FALSE if not all columns could be retrieved */ static MY_ATTRIBUTE((warn_unused_result)) ibool diff --git a/storage/innobase/row/row0trunc.cc b/storage/innobase/row/row0trunc.cc index 5724fad801f..afa49082136 100644 --- a/storage/innobase/row/row0trunc.cc +++ b/storage/innobase/row/row0trunc.cc @@ -2018,7 +2018,7 @@ row_truncate_table_for_mysql( space_size -= ib_vector_size(table->fts->indexes); } - fil_reinit_space_header(table->space, space_size, trx); + fil_reinit_space_header_for_table(table, space_size, trx); } DBUG_EXECUTE_IF("ib_trunc_crash_with_intermediate_log_checkpoint", diff --git a/storage/innobase/row/row0upd.cc b/storage/innobase/row/row0upd.cc index 34995faa2be..63f6c03187b 100644 --- a/storage/innobase/row/row0upd.cc +++ b/storage/innobase/row/row0upd.cc @@ -1,6 +1,6 @@ /***************************************************************************** -Copyright (c) 1996, 2016, Oracle and/or its affiliates. All Rights Reserved. +Copyright (c) 1996, 2017, Oracle and/or its affiliates. All Rights Reserved. Copyright (c) 2015, 2017, MariaDB Corporation. This program is free software; you can redistribute it and/or modify it under @@ -256,6 +256,9 @@ row_upd_check_references_constraints( row_mysql_freeze_data_dictionary(trx); } + DEBUG_SYNC_C_IF_THD(thr_get_trx(thr)->mysql_thd, + "foreign_constraint_check_for_insert"); + for (dict_foreign_set::iterator it = table->referenced_set.begin(); it != table->referenced_set.end(); ++it) { @@ -283,6 +286,34 @@ row_upd_check_references_constraints( FALSE, FALSE, DICT_ERR_IGNORE_NONE); } + /* dict_operation_lock is held both here + (UPDATE or DELETE with FOREIGN KEY) and by TRUNCATE + TABLE operations. + If a TRUNCATE TABLE operation is in progress, + there can be 2 possible conditions: + 1) row_truncate_table_for_mysql() is not yet called. + 2) Truncate releases dict_operation_lock + during eviction of pages from buffer pool + for a file-per-table tablespace. + + In case of (1), truncate will wait for FK operation + to complete. + In case of (2), truncate will be rolled forward even + if it is interrupted. So if the foreign table is + undergoing a truncate, ignore the FK check. */ + + if (foreign_table) { + mutex_enter(&fil_system->mutex); + const fil_space_t* space = fil_space_get_by_id( + foreign_table->space); + const bool being_truncated = space + && space->is_being_truncated; + mutex_exit(&fil_system->mutex); + if (being_truncated) { + continue; + } + } + /* NOTE that if the thread ends up waiting for a lock we will release dict_operation_lock temporarily! But the counter on the table protects 'foreign' from diff --git a/storage/innobase/sync/sync0arr.cc b/storage/innobase/sync/sync0arr.cc index 75919043731..f1589e1f3a7 100644 --- a/storage/innobase/sync/sync0arr.cc +++ b/storage/innobase/sync/sync0arr.cc @@ -621,6 +621,7 @@ sync_array_cell_print( } } +#ifdef UNIV_DEBUG /******************************************************************//** Looks for a cell with the given thread id. @return pointer to cell or NULL if not found */ @@ -648,7 +649,6 @@ sync_array_find_thread( return(NULL); /* Not found */ } -#ifdef UNIV_DEBUG /******************************************************************//** Recursion step for deadlock detection. @return TRUE if deadlock detected */ diff --git a/storage/innobase/ut/ut0rbt.cc b/storage/innobase/ut/ut0rbt.cc index d3e4ceae97d..cb8e4f2df20 100644 --- a/storage/innobase/ut/ut0rbt.cc +++ b/storage/innobase/ut/ut0rbt.cc @@ -54,6 +54,7 @@ red-black properties: #define ROOT(t) (t->root->left) #define SIZEOF_NODE(t) ((sizeof(ib_rbt_node_t) + t->sizeof_value) - 1) +#if defined UNIV_DEBUG || defined IB_RBT_TESTING /**********************************************************************//** Verify that the keys are in order. @return TRUE of OK. FALSE if not ordered */ @@ -91,6 +92,7 @@ rbt_check_ordering( return(TRUE); } +#endif /* UNIV_DEBUG || IB_RBT_TESTING */ /**********************************************************************//** Check that every path from the root to the leaves has the same count.