From c0817dac99c28698dfc2b548d89acf1fb41dc32e Mon Sep 17 00:00:00 2001 From: Vlad Lesin Date: Fri, 30 Sep 2022 19:38:59 +0300 Subject: MDEV-29575 Access to innodb_trx, innodb_locks and innodb_lock_waits along with detached XA's can cause SIGSEGV trx->mysql_thd can be zeroed-out between thd_get_thread_id() and thd_query_safe() calls in fill_trx_row(). trx_disconnect_prepared() zeroes out trx->mysql_thd. And this can cause null pointer dereferencing in fill_trx_row(). fill_trx_row() is invoked from fetch_data_into_cache() under trx_sys.mutex. Bug fix is in reseting trx_t::mysql_thd in trx_disconnect_prepared() under trx_sys.mutex lock too. MTR test case can't be created for the fix, as we need to wait for trx_t::mysql_thd reseting in fill_trx_row() after trx_t::mysql_thd was checked for null while trx_sys.mutex is held. But trx_t::mysql_thd must be reset in trx_disconnect_prepared() under trx_sys.mutex. There will be deadlock. --- storage/innobase/trx/trx0trx.cc | 2 ++ 1 file changed, 2 insertions(+) diff --git a/storage/innobase/trx/trx0trx.cc b/storage/innobase/trx/trx0trx.cc index b2cfbd9b4e3..7658af76709 100644 --- a/storage/innobase/trx/trx0trx.cc +++ b/storage/innobase/trx/trx0trx.cc @@ -564,8 +564,10 @@ void trx_disconnect_prepared(trx_t *trx) ut_ad(trx_state_eq(trx, TRX_STATE_PREPARED)); ut_ad(trx->mysql_thd); trx->read_view.close(); + mutex_enter(&trx_sys.mutex); trx->is_recovered= true; trx->mysql_thd= NULL; + mutex_exit(&trx_sys.mutex); /* todo/fixme: suggest to do it at innodb prepare */ trx->will_lock= false; } -- cgit v1.2.1 From d1bc469dca1de22bd24a4fc59a70085dcb5c32a5 Mon Sep 17 00:00:00 2001 From: Monty Date: Tue, 4 Oct 2022 11:26:50 +0300 Subject: Disable valgrind for test in main that takes > 200 seconds One can run these with --valgrind --big --- mysql-test/include/long_test.inc | 2 ++ mysql-test/main/alter_table.test | 1 + mysql-test/main/compress.test | 2 ++ mysql-test/main/ctype_big5.test | 1 + mysql-test/main/ctype_gb2312.test | 1 + mysql-test/main/ctype_gbk.test | 1 + mysql-test/main/ctype_sjis.test | 1 + mysql-test/main/ctype_utf8.test | 1 + mysql-test/main/gis-precise.test | 4 ++-- mysql-test/main/group_min_max.test | 1 + mysql-test/main/index_merge_innodb.test | 1 + mysql-test/main/index_merge_myisam.test | 1 + mysql-test/main/information_schema_all_engines.test | 1 + mysql-test/main/innodb_ext_key.test | 1 + mysql-test/main/join_cache.test | 6 ++++-- mysql-test/main/mysql_client_test_comp.test | 1 + mysql-test/main/mysql_upgrade.test | 1 + mysql-test/main/mysqldump.test | 1 + mysql-test/main/order_by.test | 1 + mysql-test/main/pool_of_threads.test | 3 ++- mysql-test/main/query_cache.test | 1 + mysql-test/main/query_cache_debug.test | 1 + mysql-test/main/range.test | 1 + mysql-test/main/range_innodb.test | 1 + mysql-test/main/range_vs_index_merge.test | 1 + mysql-test/main/rowid_filter_innodb.test | 1 + mysql-test/main/select.test | 2 ++ mysql-test/main/selectivity.test | 1 + mysql-test/main/sp.test | 1 + mysql-test/main/ssl.test | 1 + mysql-test/main/stat_tables_disabled.test | 2 ++ mysql-test/main/stat_tables_innodb.test | 1 + mysql-test/main/stat_tables_par_innodb.test | 1 + mysql-test/main/statistics.test | 1 + mysql-test/main/subselect_innodb.test | 1 + mysql-test/main/subselect_sj.test | 1 + mysql-test/main/subselect_sj_jcl6.test | 1 + mysql-test/main/trigger.test | 3 ++- mysql-test/main/win.test | 1 + mysql-test/main/win_big-mdev-11697.test | 2 ++ 40 files changed, 51 insertions(+), 6 deletions(-) diff --git a/mysql-test/include/long_test.inc b/mysql-test/include/long_test.inc index d9a3b338229..765f88b8037 100644 --- a/mysql-test/include/long_test.inc +++ b/mysql-test/include/long_test.inc @@ -2,3 +2,5 @@ # We can use this to schedule such test early (to not be left with # only one or two long tests running, and rests of works idle), or to # run a quick test skipping long-running test cases. + +--source include/no_valgrind_without_big.inc diff --git a/mysql-test/main/alter_table.test b/mysql-test/main/alter_table.test index 6dcb441d30a..ec2b5e2b1f0 100644 --- a/mysql-test/main/alter_table.test +++ b/mysql-test/main/alter_table.test @@ -1,3 +1,4 @@ +--source include/no_valgrind_without_big.inc --source include/have_innodb.inc # # Test of alter table diff --git a/mysql-test/main/compress.test b/mysql-test/main/compress.test index 8fc21d9c961..daa133ebdc7 100644 --- a/mysql-test/main/compress.test +++ b/mysql-test/main/compress.test @@ -1,6 +1,8 @@ # Turn on compression between the client and server # and run a number of tests +# Too slow for valgrind +--source include/no_valgrind_without_big.inc # Can't test with embedded server -- source include/not_embedded.inc -- source include/have_compress.inc diff --git a/mysql-test/main/ctype_big5.test b/mysql-test/main/ctype_big5.test index 410203c7c86..3d81686b767 100644 --- a/mysql-test/main/ctype_big5.test +++ b/mysql-test/main/ctype_big5.test @@ -1,3 +1,4 @@ +-- source include/no_valgrind_without_big.inc -- source include/have_big5.inc # diff --git a/mysql-test/main/ctype_gb2312.test b/mysql-test/main/ctype_gb2312.test index 4489168a163..9cd7834a287 100644 --- a/mysql-test/main/ctype_gb2312.test +++ b/mysql-test/main/ctype_gb2312.test @@ -1,3 +1,4 @@ +-- source include/no_valgrind_without_big.inc -- source include/have_gb2312.inc # diff --git a/mysql-test/main/ctype_gbk.test b/mysql-test/main/ctype_gbk.test index d9d0a4d0ee4..defaf8bf6c3 100644 --- a/mysql-test/main/ctype_gbk.test +++ b/mysql-test/main/ctype_gbk.test @@ -1,3 +1,4 @@ +--source include/no_valgrind_without_big.inc -- source include/have_gbk.inc # diff --git a/mysql-test/main/ctype_sjis.test b/mysql-test/main/ctype_sjis.test index 00662fdf2a0..13250b4933f 100644 --- a/mysql-test/main/ctype_sjis.test +++ b/mysql-test/main/ctype_sjis.test @@ -1,3 +1,4 @@ +-- source include/no_valgrind_without_big.inc -- source include/have_sjis.inc # diff --git a/mysql-test/main/ctype_utf8.test b/mysql-test/main/ctype_utf8.test index e2c47e75993..291149b317e 100644 --- a/mysql-test/main/ctype_utf8.test +++ b/mysql-test/main/ctype_utf8.test @@ -1,3 +1,4 @@ +--source include/no_valgrind_without_big.inc # # Tests with the utf8 character set # diff --git a/mysql-test/main/gis-precise.test b/mysql-test/main/gis-precise.test index da72a0c4d8a..f49b3f1a1da 100644 --- a/mysql-test/main/gis-precise.test +++ b/mysql-test/main/gis-precise.test @@ -1,5 +1,5 @@ --- source include/have_geometry.inc - +--source include/no_valgrind_without_big.inc +--source include/have_geometry.inc # # Spatial objects diff --git a/mysql-test/main/group_min_max.test b/mysql-test/main/group_min_max.test index 0dc7ea2fee7..506323599cb 100644 --- a/mysql-test/main/group_min_max.test +++ b/mysql-test/main/group_min_max.test @@ -3,6 +3,7 @@ # The queries in this file test query execution via QUICK_GROUP_MIN_MAX_SELECT. # +--source include/no_valgrind_without_big.inc --source include/default_optimizer_switch.inc # diff --git a/mysql-test/main/index_merge_innodb.test b/mysql-test/main/index_merge_innodb.test index 4bdcb17760e..7931f6912dd 100644 --- a/mysql-test/main/index_merge_innodb.test +++ b/mysql-test/main/index_merge_innodb.test @@ -11,6 +11,7 @@ # # Slow test, don't run during staging part +--source include/long_test.inc --source include/not_staging.inc --source include/have_innodb.inc diff --git a/mysql-test/main/index_merge_myisam.test b/mysql-test/main/index_merge_myisam.test index b77c9bc1ca2..c098d80688b 100644 --- a/mysql-test/main/index_merge_myisam.test +++ b/mysql-test/main/index_merge_myisam.test @@ -9,6 +9,7 @@ # wrapper t/index_merge_innodb.test sources now several # include/index_merge*.inc files # +--source include/no_valgrind_without_big.inc SET STORAGE_ENGINE = MyISAM; # MyISAM supports Merge tables diff --git a/mysql-test/main/information_schema_all_engines.test b/mysql-test/main/information_schema_all_engines.test index f8d685d2560..04537051acb 100644 --- a/mysql-test/main/information_schema_all_engines.test +++ b/mysql-test/main/information_schema_all_engines.test @@ -2,6 +2,7 @@ # information_schema_db.test whose results depends on which engines are # available (since these engines inject tables into INFORMATION_SCHEMA). +--source include/no_valgrind_without_big.inc --source include/not_embedded.inc --source include/have_innodb.inc --source include/have_perfschema.inc diff --git a/mysql-test/main/innodb_ext_key.test b/mysql-test/main/innodb_ext_key.test index 1ff0ea51990..2de8be92149 100644 --- a/mysql-test/main/innodb_ext_key.test +++ b/mysql-test/main/innodb_ext_key.test @@ -1,4 +1,5 @@ --source include/innodb_prefix_index_cluster_optimization.inc +--source include/no_valgrind_without_big.inc SET SESSION STORAGE_ENGINE='InnoDB'; diff --git a/mysql-test/main/join_cache.test b/mysql-test/main/join_cache.test index b4271f648e3..b5d21179f43 100644 --- a/mysql-test/main/join_cache.test +++ b/mysql-test/main/join_cache.test @@ -1,9 +1,11 @@ +--source include/no_valgrind_without_big.inc +--source include/default_optimizer_switch.inc +--source include/default_charset.inc + --disable_warnings DROP TABLE IF EXISTS t1,t2,t3,t4,t5,t6,t7,t8,t9,t10,t11; DROP DATABASE IF EXISTS world; --enable_warnings ---source include/default_optimizer_switch.inc ---source include/default_charset.inc set @org_optimizer_switch=@@optimizer_switch; set @save_join_cache_level=@@join_cache_level; diff --git a/mysql-test/main/mysql_client_test_comp.test b/mysql-test/main/mysql_client_test_comp.test index f8bd80fc48a..36a12b6691e 100644 --- a/mysql-test/main/mysql_client_test_comp.test +++ b/mysql-test/main/mysql_client_test_comp.test @@ -3,6 +3,7 @@ # No need to run this with embedded server --source include/not_embedded.inc --source include/check_ipv6.inc +--source include/no_valgrind_without_big.inc # need to have the dynamic loading turned on for the client plugin tests --source include/have_plugin_auth.inc diff --git a/mysql-test/main/mysql_upgrade.test b/mysql-test/main/mysql_upgrade.test index b0a1ffaa9d9..edf2cb21b05 100644 --- a/mysql-test/main/mysql_upgrade.test +++ b/mysql-test/main/mysql_upgrade.test @@ -2,6 +2,7 @@ -- source include/have_working_dns.inc -- source include/have_innodb.inc -- source include/have_partition.inc +-- source include/no_valgrind_without_big.inc set sql_mode=""; diff --git a/mysql-test/main/mysqldump.test b/mysql-test/main/mysqldump.test index 66b2259579a..d1b0a7d8c84 100644 --- a/mysql-test/main/mysqldump.test +++ b/mysql-test/main/mysqldump.test @@ -1,3 +1,4 @@ +--source include/no_valgrind_without_big.inc --source include/have_utf8mb4.inc call mtr.add_suppression("@003f.frm' \\(errno: 22\\)"); diff --git a/mysql-test/main/order_by.test b/mysql-test/main/order_by.test index 9ba2b49a5a8..5f83f0f7541 100644 --- a/mysql-test/main/order_by.test +++ b/mysql-test/main/order_by.test @@ -1,3 +1,4 @@ +--source include/no_valgrind_without_big.inc # # Testing ORDER BY # diff --git a/mysql-test/main/pool_of_threads.test b/mysql-test/main/pool_of_threads.test index 3d581d4605d..e9f083b2f8f 100644 --- a/mysql-test/main/pool_of_threads.test +++ b/mysql-test/main/pool_of_threads.test @@ -4,10 +4,11 @@ -- source include/have_pool_of_threads.inc -- source include/default_optimizer_switch.inc -SET optimizer_switch='outer_join_with_cache=off'; # Slow test, don't run during staging part -- source include/not_staging.inc -- source include/long_test.inc + +SET optimizer_switch='outer_join_with_cache=off'; -- source include/common-tests.inc SET optimizer_switch=default; diff --git a/mysql-test/main/query_cache.test b/mysql-test/main/query_cache.test index 6e113f0cdb7..9bb5122bc46 100644 --- a/mysql-test/main/query_cache.test +++ b/mysql-test/main/query_cache.test @@ -1,5 +1,6 @@ -- source include/have_query_cache.inc -- source include/long_test.inc +-- source include/no_valgrind_without_big.inc set @save_query_cache_size=@@query_cache_size; # diff --git a/mysql-test/main/query_cache_debug.test b/mysql-test/main/query_cache_debug.test index af82927245b..056396984d9 100644 --- a/mysql-test/main/query_cache_debug.test +++ b/mysql-test/main/query_cache_debug.test @@ -2,6 +2,7 @@ --source include/have_query_cache.inc --source include/have_debug_sync.inc --source include/long_test.inc +--source include/no_valgrind_without_big.inc set global query_cache_type= ON; set @save_query_cache_size=@@global.query_cache_size; diff --git a/mysql-test/main/range.test b/mysql-test/main/range.test index 10245857265..100b875e66f 100644 --- a/mysql-test/main/range.test +++ b/mysql-test/main/range.test @@ -1,3 +1,4 @@ +--source include/no_valgrind_without_big.inc # # Problem with range optimizer # diff --git a/mysql-test/main/range_innodb.test b/mysql-test/main/range_innodb.test index 8b9771d1d1e..a9fef01b941 100644 --- a/mysql-test/main/range_innodb.test +++ b/mysql-test/main/range_innodb.test @@ -4,6 +4,7 @@ --source include/have_innodb.inc --source include/have_debug.inc +--source include/no_valgrind_without_big.inc --disable_warnings drop table if exists t0, t1, t2; diff --git a/mysql-test/main/range_vs_index_merge.test b/mysql-test/main/range_vs_index_merge.test index 94210ce5dd3..e9854386b98 100644 --- a/mysql-test/main/range_vs_index_merge.test +++ b/mysql-test/main/range_vs_index_merge.test @@ -1,3 +1,4 @@ +--source include/no_valgrind_without_big.inc --source include/default_optimizer_switch.inc --source include/default_charset.inc --source include/have_sequence.inc diff --git a/mysql-test/main/rowid_filter_innodb.test b/mysql-test/main/rowid_filter_innodb.test index d121405f08d..dc8b1ddbca5 100644 --- a/mysql-test/main/rowid_filter_innodb.test +++ b/mysql-test/main/rowid_filter_innodb.test @@ -1,3 +1,4 @@ +--source include/no_valgrind_without_big.inc --source include/have_innodb.inc SET SESSION STORAGE_ENGINE='InnoDB'; diff --git a/mysql-test/main/select.test b/mysql-test/main/select.test index 407108e6206..0e19ddd6970 100644 --- a/mysql-test/main/select.test +++ b/mysql-test/main/select.test @@ -2,6 +2,8 @@ # Find string "NOTE NOTE NOTE" in order to find some 'unsure' tests # +--source include/no_valgrind_without_big.inc + # # Simple select test # diff --git a/mysql-test/main/selectivity.test b/mysql-test/main/selectivity.test index 1d96dc0bf80..ba0af502720 100644 --- a/mysql-test/main/selectivity.test +++ b/mysql-test/main/selectivity.test @@ -1,3 +1,4 @@ +--source include/no_valgrind_without_big.inc --source include/have_stat_tables.inc --source include/have_sequence.inc --source include/default_charset.inc diff --git a/mysql-test/main/sp.test b/mysql-test/main/sp.test index a93689ba4da..68aa40a9d29 100644 --- a/mysql-test/main/sp.test +++ b/mysql-test/main/sp.test @@ -1,3 +1,4 @@ +--source include/no_valgrind_without_big.inc --source include/have_partition.inc --source include/have_sequence.inc diff --git a/mysql-test/main/ssl.test b/mysql-test/main/ssl.test index 45c903d43d2..8812c792a47 100644 --- a/mysql-test/main/ssl.test +++ b/mysql-test/main/ssl.test @@ -1,3 +1,4 @@ +--source include/no_valgrind_without_big.inc # Turn on ssl between the client and server # and run a number of tests diff --git a/mysql-test/main/stat_tables_disabled.test b/mysql-test/main/stat_tables_disabled.test index 427cf4874bc..0ba698da752 100644 --- a/mysql-test/main/stat_tables_disabled.test +++ b/mysql-test/main/stat_tables_disabled.test @@ -4,7 +4,9 @@ set @innodb_stats_persistent_sample_pages_save= set global innodb_stats_persistent= 1; set global innodb_stats_persistent_sample_pages=100; + --source include/have_innodb.inc +--source include/no_valgrind_without_big.inc SET SESSION STORAGE_ENGINE='InnoDB'; diff --git a/mysql-test/main/stat_tables_innodb.test b/mysql-test/main/stat_tables_innodb.test index 301ee8692b9..940eaf23855 100644 --- a/mysql-test/main/stat_tables_innodb.test +++ b/mysql-test/main/stat_tables_innodb.test @@ -1,3 +1,4 @@ +--source include/no_valgrind_without_big.inc --source include/have_innodb.inc --source include/have_sequence.inc diff --git a/mysql-test/main/stat_tables_par_innodb.test b/mysql-test/main/stat_tables_par_innodb.test index fd5833e4aaf..f62777b9cf7 100644 --- a/mysql-test/main/stat_tables_par_innodb.test +++ b/mysql-test/main/stat_tables_par_innodb.test @@ -1,3 +1,4 @@ +--source include/no_valgrind_without_big.inc --source include/have_innodb.inc SET SESSION STORAGE_ENGINE='InnoDB'; diff --git a/mysql-test/main/statistics.test b/mysql-test/main/statistics.test index 1f99aaa33e5..a81de1662f0 100644 --- a/mysql-test/main/statistics.test +++ b/mysql-test/main/statistics.test @@ -1,3 +1,4 @@ +--source include/no_valgrind_without_big.inc --source include/have_stat_tables.inc --source include/have_innodb.inc --disable_warnings diff --git a/mysql-test/main/subselect_innodb.test b/mysql-test/main/subselect_innodb.test index fef954edc28..1007dadffdd 100644 --- a/mysql-test/main/subselect_innodb.test +++ b/mysql-test/main/subselect_innodb.test @@ -1,3 +1,4 @@ +-- source include/no_valgrind_without_big.inc -- source include/have_innodb.inc # Note: the tests uses only non-semijoin subqueries so semi-join switch diff --git a/mysql-test/main/subselect_sj.test b/mysql-test/main/subselect_sj.test index c869f56c837..e4d02ed666c 100644 --- a/mysql-test/main/subselect_sj.test +++ b/mysql-test/main/subselect_sj.test @@ -1,3 +1,4 @@ +--source include/no_valgrind_without_big.inc # # Nested Loops semi-join subquery evaluation tests # diff --git a/mysql-test/main/subselect_sj_jcl6.test b/mysql-test/main/subselect_sj_jcl6.test index 179c1aa029b..f4f605c0406 100644 --- a/mysql-test/main/subselect_sj_jcl6.test +++ b/mysql-test/main/subselect_sj_jcl6.test @@ -1,6 +1,7 @@ # # Run subselect_sj.test with BKA enabled # +--source include/no_valgrind_without_big.inc --source include/default_optimizer_switch.inc set @save_optimizer_switch_jcl6=@@optimizer_switch; diff --git a/mysql-test/main/trigger.test b/mysql-test/main/trigger.test index 56e9246b95c..e8cc64adf40 100644 --- a/mysql-test/main/trigger.test +++ b/mysql-test/main/trigger.test @@ -1,6 +1,7 @@ # This test uses chmod, can't be run with root permissions -- source include/not_as_root.inc ---source include/default_charset.inc +-- source include/no_valgrind_without_big.inc +-- source include/default_charset.inc # # Basic triggers test diff --git a/mysql-test/main/win.test b/mysql-test/main/win.test index ce32626510a..01baaa138bc 100644 --- a/mysql-test/main/win.test +++ b/mysql-test/main/win.test @@ -1,6 +1,7 @@ # # Window Functions Tests # +--source include/no_valgrind_without_big.inc --source include/have_sequence.inc --disable_warnings diff --git a/mysql-test/main/win_big-mdev-11697.test b/mysql-test/main/win_big-mdev-11697.test index 7103b8522be..aca15fa9944 100644 --- a/mysql-test/main/win_big-mdev-11697.test +++ b/mysql-test/main/win_big-mdev-11697.test @@ -1,3 +1,5 @@ +--source include/no_valgrind_without_big.inc + create table test_table (id int, random_data varchar(36), static_int int, static_varchar varchar(10)); insert into test_table(id, random_data, static_int, static_varchar) -- cgit v1.2.1 From 19f0b96d53dec47d7b8680c44997afba2ed7431e Mon Sep 17 00:00:00 2001 From: Julius Goryavsky Date: Tue, 4 Oct 2022 13:15:52 +0200 Subject: MDEV-27682: bundled wsrep_notify.sh causes mariadbd to freeze during start This commit adds automation that will reduce the possibility of user errors when customizing wsrep_notify.sh (in particular caused by user-specified parameters). Now all leading and trailing spaces are removed from the user-specified parameters and automatic port and host address substitution has been added to scripts, as well as automatic password substitution to the client command line, only if it is specified in the wsrep_notify.sh and not as empty strings. Also added support for automatic substitution of the all SSL-related parameters and improved parsing for ipv6 addresses (to allow "[...]" notation for ipv6 addresses). Also added a test to check if the wsrep notify script will works with SSL. --- mysql-test/include/ipv6.inc | 1 - mysql-test/std_data/wsrep_notify.sh | 124 +++++++++++-- mysql-test/std_data/wsrep_notify_ssl.sh | 195 +++++++++++++++++++++ .../galera/r/galera_var_notify_ssl_ipv6.result | 11 ++ .../galera/t/galera_var_notify_ssl_ipv6-master.opt | 1 + .../suite/galera/t/galera_var_notify_ssl_ipv6.cnf | 20 +++ .../suite/galera/t/galera_var_notify_ssl_ipv6.test | 20 +++ support-files/wsrep_notify.sh | 123 +++++++++++-- 8 files changed, 465 insertions(+), 30 deletions(-) create mode 100755 mysql-test/std_data/wsrep_notify_ssl.sh create mode 100644 mysql-test/suite/galera/r/galera_var_notify_ssl_ipv6.result create mode 100644 mysql-test/suite/galera/t/galera_var_notify_ssl_ipv6-master.opt create mode 100644 mysql-test/suite/galera/t/galera_var_notify_ssl_ipv6.cnf create mode 100644 mysql-test/suite/galera/t/galera_var_notify_ssl_ipv6.test mode change 100644 => 100755 support-files/wsrep_notify.sh diff --git a/mysql-test/include/ipv6.inc b/mysql-test/include/ipv6.inc index 3d8fdcfbc3c..05c65d7817a 100644 --- a/mysql-test/include/ipv6.inc +++ b/mysql-test/include/ipv6.inc @@ -22,4 +22,3 @@ eval SET PASSWORD FOR testuser1@'$IPv6' = PASSWORD ('9876'); --replace_result ::1 localhost SELECT USER(); eval DROP USER testuser1@'$IPv6'; - diff --git a/mysql-test/std_data/wsrep_notify.sh b/mysql-test/std_data/wsrep_notify.sh index 7036f603c84..d5defd6420e 100755 --- a/mysql-test/std_data/wsrep_notify.sh +++ b/mysql-test/std_data/wsrep_notify.sh @@ -4,11 +4,31 @@ # It will create 'wsrep' schema and two tables in it: 'membeship' and 'status' # and fill them on every membership or node status change. # -# Edit parameters below to specify the address and login to server. - +# Edit parameters below to specify the address and login to server: +# USER=root +PSWD= +# +# If these parameters are not set, then the values +# passed by the server are taken: +# HOST=127.0.0.1 PORT=$NODE_MYPORT_1 +# +# Edit parameters below to specify SSL parameters: +# +ssl_key= +ssl_cert= +ssl_ca= +ssl_capath= +ssl_cipher= +ssl_crl= +ssl_crlpath= +ssl_verify_server_cert=0 +# +# Client executable path: +# +CLIENT="$EXE_MYSQL" SCHEMA="mtr_wsrep_notify" MEMB_TABLE="$SCHEMA.membership" @@ -19,7 +39,7 @@ SET wsrep_on=0; CREATE SCHEMA IF NOT EXISTS $SCHEMA; CREATE TABLE IF NOT EXISTS $MEMB_TABLE ( idx INT, - uuid CHAR(40), /* node UUID */ + uuid CHAR(40), /* node UUID */ name VARCHAR(32), /* node name */ addr VARCHAR(256) /* node address */ ) ENGINE=MEMORY; @@ -40,7 +60,7 @@ configuration_change() local idx=0 - for NODE in $(echo $MEMBERS | sed s/,/\ /g) + for NODE in $(echo "$MEMBERS" | sed s/,/\ /g) do echo "INSERT INTO $MEMB_TABLE VALUES ( $idx, " # Don't forget to properly quote string values @@ -59,17 +79,44 @@ status_update() echo "SET wsrep_on=0; BEGIN; UPDATE $STATUS_TABLE SET status='$STATUS'; COMMIT;" } +trim_string() +{ + if [ -n "${BASH_VERSION:-}" ]; then + local pattern="[![:space:]${2:-}]" + local x="${1#*$pattern}" + local z=${#1} + x=${#x} + if [ $x -ne $z ]; then + local y="${1%$pattern*}" + y=${#y} + x=$(( z-x-1 )) + y=$(( y-x+1 )) + printf '%s' "${1:$x:$y}" + else + printf '' + fi + else + local pattern="[[:space:]${2:-}]" + echo "$1" | sed -E "s/^$pattern+|$pattern+\$//g" + fi +} + COM=status_update # not a configuration change by default -while [ $# -gt 0 ] -do +STATUS="" +CLUSTER_UUID="" +PRIMARY="0" +INDEX="" +MEMBERS="" + +while [ $# -gt 0 ]; do case $1 in --status) - STATUS=$2 + STATUS=$(trim_string "$2") shift ;; --uuid) - CLUSTER_UUID=$2 + CLUSTER_UUID=$(trim_string "$2") shift ;; --primary) @@ -78,22 +125,71 @@ do shift ;; --index) - INDEX=$2 + INDEX=$(trim_string "$2") shift ;; --members) - MEMBERS=$2 + MEMBERS=$(trim_string "$2") shift ;; esac shift done -# Undefined means node is shutting down -if [ "$STATUS" != "Undefined" ] +USER=$(trim_string "$USER") +PSWD=$(trim_string "$PSWD") + +HOST=$(trim_string "$HOST") +PORT=$(trim_string "$PORT") + +case "$HOST" in +\[*) + HOST="${HOST##\[}" + HOST=$(trim_string "${HOST%%\]}") + ;; +esac + +if [ -z "$HOST" ]; then + HOST="${NOTIFY_HOST:-}" +fi +if [ -z "$PORT" ]; then + PORT="${NOTIFY_PORT:-}" +fi + +ssl_key=$(trim_string "$ssl_key"); +ssl_cert=$(trim_string "$ssl_cert"); +ssl_ca=$(trim_string "$ssl_ca"); +ssl_capath=$(trim_string "$ssl_capath"); +ssl_cipher=$(trim_string "$ssl_cipher"); +ssl_crl=$(trim_string "$ssl_crl"); +ssl_crlpath=$(trim_string "$ssl_crlpath"); +ssl_verify_server_cert=$(trim_string "$ssl_verify_server_cert"); + +SSL_PARAM="" + +if [ -n "$ssl_key" -o -n "$ssl_cert" -o \ + -n "$ssl_ca" -o -n "$ssl_capath" -o \ + -n "$ssl_cipher" ] then - $COM | mysql -B -u$USER -h$HOST -P$PORT + SSL_PARAM=' --ssl' + [ -n "$ssl_key" ] && SSL_PARAM="$SSL_PARAM --ssl-key='$ssl_key'" + [ -n "$ssl_cert" ] && SSL_PARAM="$SSL_PARAM --ssl-cert='$ssl_cert'" + [ -n "$ssl_ca" ] && SSL_PARAM="$SSL_PARAM --ssl-ca='$ssl_ca'" + [ -n "$ssl_capath" ] && SSL_PARAM="$SSL_PARAM --ssl-capath='$ssl_capath'" + [ -n "$ssl_cipher" ] && SSL_PARAM="$SSL_PARAM --ssl-cipher='$ssl_cipher'" + [ -n "$ssl_crl" ] && SSL_PARAM="$SSL_PARAM --ssl-crl='$ssl_crl'" + [ -n "$ssl_crlpath" ] && SSL_PARAM="$SSL_PARAM --ssl-crlpath='$ssl_crlpath'" + if [ -n "$ssl_verify_server_cert" ]; then + if [ $ssl_verify_server_cert -ne 0 ]; then + SSL_PARAM+=' --ssl-verify-server-cert' + fi + fi +fi + +# Undefined means node is shutting down +if [ "$STATUS" != 'Undefined' ]; then + "$COM" | eval "$CLIENT" -B "-u'$USER'"${PSWD:+" -p'$PSWD'"}\ + "-h'$HOST'" "-P$PORT"$SSL_PARAM fi exit 0 -# diff --git a/mysql-test/std_data/wsrep_notify_ssl.sh b/mysql-test/std_data/wsrep_notify_ssl.sh new file mode 100755 index 00000000000..0e416a2f448 --- /dev/null +++ b/mysql-test/std_data/wsrep_notify_ssl.sh @@ -0,0 +1,195 @@ +#!/bin/sh -eu + +# This is a simple example of wsrep notification script (wsrep_notify_cmd). +# It will create 'wsrep' schema and two tables in it: 'membeship' and 'status' +# and fill them on every membership or node status change. +# +# Edit parameters below to specify the address and login to server: +# +USER=root +PSWD= +# +# If these parameters are not set, then the values +# passed by the server are taken: +# +HOST=127.0.0.1 +PORT=$NODE_MYPORT_1 +# +# Edit parameters below to specify SSL parameters: +# +ssl_cert="$MYSQL_TEST_DIR/std_data/client-cert.pem" +ssl_key="$MYSQL_TEST_DIR/std_data/client-key.pem" +ssl_ca="$MYSQL_TEST_DIR/std_data/cacert.pem" +ssl_capath= +ssl_cipher= +ssl_crl= +ssl_crlpath= +ssl_verify_server_cert=0 +# +# Client executable path: +# +CLIENT="$EXE_MYSQL" + +SCHEMA="mtr_wsrep_notify" +MEMB_TABLE="$SCHEMA.membership" +STATUS_TABLE="$SCHEMA.status" + +BEGIN=" +SET wsrep_on=0; +CREATE SCHEMA IF NOT EXISTS $SCHEMA; +CREATE TABLE IF NOT EXISTS $MEMB_TABLE ( + idx INT, + uuid CHAR(40), /* node UUID */ + name VARCHAR(32), /* node name */ + addr VARCHAR(256) /* node address */ +) ENGINE=MEMORY; +CREATE TABLE IF NOT EXISTS $STATUS_TABLE ( + size INT, /* component size */ + idx INT, /* this node index */ + status CHAR(16), /* this node status */ + uuid CHAR(40), /* cluster UUID */ + prim BOOLEAN /* if component is primary */ +) ENGINE=MEMORY; +BEGIN; +" +END="COMMIT;" + +configuration_change() +{ + echo "$BEGIN;" + + local idx=0 + + for NODE in $(echo "$MEMBERS" | sed s/,/\ /g) + do + echo "INSERT INTO $MEMB_TABLE VALUES ( $idx, " + # Don't forget to properly quote string values + echo "'$NODE'" | sed s/\\//\',\'/g + echo ");" + idx=$(( $idx + 1 )) + done + + echo "INSERT INTO $STATUS_TABLE VALUES($idx, $INDEX, '$STATUS', '$CLUSTER_UUID', $PRIMARY);" + + echo "$END" +} + +status_update() +{ + echo "SET wsrep_on=0; BEGIN; UPDATE $STATUS_TABLE SET status='$STATUS'; COMMIT;" +} + +trim_string() +{ + if [ -n "${BASH_VERSION:-}" ]; then + local pattern="[![:space:]${2:-}]" + local x="${1#*$pattern}" + local z=${#1} + x=${#x} + if [ $x -ne $z ]; then + local y="${1%$pattern*}" + y=${#y} + x=$(( z-x-1 )) + y=$(( y-x+1 )) + printf '%s' "${1:$x:$y}" + else + printf '' + fi + else + local pattern="[[:space:]${2:-}]" + echo "$1" | sed -E "s/^$pattern+|$pattern+\$//g" + fi +} + +COM=status_update # not a configuration change by default + +STATUS="" +CLUSTER_UUID="" +PRIMARY="0" +INDEX="" +MEMBERS="" + +while [ $# -gt 0 ]; do + case $1 in + --status) + STATUS=$(trim_string "$2") + shift + ;; + --uuid) + CLUSTER_UUID=$(trim_string "$2") + shift + ;; + --primary) + [ "$2" = "yes" ] && PRIMARY="1" || PRIMARY="0" + COM=configuration_change + shift + ;; + --index) + INDEX=$(trim_string "$2") + shift + ;; + --members) + MEMBERS=$(trim_string "$2") + shift + ;; + esac + shift +done + +USER=$(trim_string "$USER") +PSWD=$(trim_string "$PSWD") + +HOST=$(trim_string "$HOST") +PORT=$(trim_string "$PORT") + +case "$HOST" in +\[*) + HOST="${HOST##\[}" + HOST=$(trim_string "${HOST%%\]}") + ;; +esac + +if [ -z "$HOST" ]; then + HOST="${NOTIFY_HOST:-}" +fi +if [ -z "$PORT" ]; then + PORT="${NOTIFY_PORT:-}" +fi + +ssl_key=$(trim_string "$ssl_key"); +ssl_cert=$(trim_string "$ssl_cert"); +ssl_ca=$(trim_string "$ssl_ca"); +ssl_capath=$(trim_string "$ssl_capath"); +ssl_cipher=$(trim_string "$ssl_cipher"); +ssl_crl=$(trim_string "$ssl_crl"); +ssl_crlpath=$(trim_string "$ssl_crlpath"); +ssl_verify_server_cert=$(trim_string "$ssl_verify_server_cert"); + +SSL_PARAM="" + +if [ -n "$ssl_key" -o -n "$ssl_cert" -o \ + -n "$ssl_ca" -o -n "$ssl_capath" -o \ + -n "$ssl_cipher" ] +then + SSL_PARAM=' --ssl' + [ -n "$ssl_key" ] && SSL_PARAM="$SSL_PARAM --ssl-key='$ssl_key'" + [ -n "$ssl_cert" ] && SSL_PARAM="$SSL_PARAM --ssl-cert='$ssl_cert'" + [ -n "$ssl_ca" ] && SSL_PARAM="$SSL_PARAM --ssl-ca='$ssl_ca'" + [ -n "$ssl_capath" ] && SSL_PARAM="$SSL_PARAM --ssl-capath='$ssl_capath'" + [ -n "$ssl_cipher" ] && SSL_PARAM="$SSL_PARAM --ssl-cipher='$ssl_cipher'" + [ -n "$ssl_crl" ] && SSL_PARAM="$SSL_PARAM --ssl-crl='$ssl_crl'" + [ -n "$ssl_crlpath" ] && SSL_PARAM="$SSL_PARAM --ssl-crlpath='$ssl_crlpath'" + if [ -n "$ssl_verify_server_cert" ]; then + if [ $ssl_verify_server_cert -ne 0 ]; then + SSL_PARAM+=' --ssl-verify-server-cert' + fi + fi +fi + +# Undefined means node is shutting down +if [ "$STATUS" != 'Undefined' ]; then + "$COM" | eval "$CLIENT" -B "-u'$USER'"${PSWD:+" -p'$PSWD'"}\ + "-h'$HOST'" "-P$PORT"$SSL_PARAM +fi + +exit 0 diff --git a/mysql-test/suite/galera/r/galera_var_notify_ssl_ipv6.result b/mysql-test/suite/galera/r/galera_var_notify_ssl_ipv6.result new file mode 100644 index 00000000000..823407fbba7 --- /dev/null +++ b/mysql-test/suite/galera/r/galera_var_notify_ssl_ipv6.result @@ -0,0 +1,11 @@ +connection node_1; +SELECT COUNT(DISTINCT uuid) AS EXPECT_2 FROM mtr_wsrep_notify.membership; +EXPECT_2 +2 +SELECT MAX(size) AS EXPECT_2 FROM mtr_wsrep_notify.status; +EXPECT_2 +2 +SELECT COUNT(DISTINCT idx) AS EXPECT_2 FROM mtr_wsrep_notify.status; +EXPECT_2 +2 +DROP SCHEMA mtr_wsrep_notify; diff --git a/mysql-test/suite/galera/t/galera_var_notify_ssl_ipv6-master.opt b/mysql-test/suite/galera/t/galera_var_notify_ssl_ipv6-master.opt new file mode 100644 index 00000000000..99c5889916b --- /dev/null +++ b/mysql-test/suite/galera/t/galera_var_notify_ssl_ipv6-master.opt @@ -0,0 +1 @@ +--wsrep_notify_cmd=$MYSQL_TEST_DIR/std_data/wsrep_notify_ssl.sh --wsrep-sync-wait=0 diff --git a/mysql-test/suite/galera/t/galera_var_notify_ssl_ipv6.cnf b/mysql-test/suite/galera/t/galera_var_notify_ssl_ipv6.cnf new file mode 100644 index 00000000000..ce121d20e03 --- /dev/null +++ b/mysql-test/suite/galera/t/galera_var_notify_ssl_ipv6.cnf @@ -0,0 +1,20 @@ +!include ../galera_2nodes.cnf + +[mysqld] +ssl-cert=@ENV.MYSQL_TEST_DIR/std_data/server-cert.pem +ssl-key=@ENV.MYSQL_TEST_DIR/std_data/server-key.pem +ssl-ca=@ENV.MYSQL_TEST_DIR/std_data/cacert.pem +bind-address=:: + +[mysqld.1] +wsrep_provider_options='base_port=@mysqld.1.#galera_port;gmcast.listen_addr=tcp://[::]:@mysqld.1.#galera_port;ist.recv_addr=[::1]:@mysqld.1.#ist_port;gcache.size=1;pc.ignore_sb=true' +wsrep_node_incoming_address='[::1]:@mysqld.1.port' +wsrep_node_address=::1 +wsrep_sst_receive_address='[::1]:@mysqld.1.#sst_port' + +[mysqld.2] +wsrep_cluster_address='gcomm://[::1]:@mysqld.1.#galera_port' +wsrep_provider_options='base_port=@mysqld.2.#galera_port;gmcast.listen_addr=tcp://[::]:@mysqld.2.#galera_port;ist.recv_addr=[::1]:@mysqld.2.#ist_port;gcache.size=1;pc.ignore_sb=true' +wsrep_node_address=::1 +wsrep_node_incoming_address='[::1]:@mysqld.2.port' +wsrep_sst_receive_address='[::1]:@mysqld.2.#sst_port' diff --git a/mysql-test/suite/galera/t/galera_var_notify_ssl_ipv6.test b/mysql-test/suite/galera/t/galera_var_notify_ssl_ipv6.test new file mode 100644 index 00000000000..2c2b106c2ae --- /dev/null +++ b/mysql-test/suite/galera/t/galera_var_notify_ssl_ipv6.test @@ -0,0 +1,20 @@ +# +# Test wsrep_notify_cmd. We use a version of the support-files/wsrep_notify.sh script that writes +# notifications into a table. +# + +--source include/galera_cluster.inc +--source include/have_ssl_communication.inc +--source include/check_ipv6.inc +--source include/force_restart.inc + +--connection node_1 +--let $wait_condition = SELECT COUNT(DISTINCT uuid) = 2 FROM mtr_wsrep_notify.membership; +--source include/wait_condition.inc + +SELECT COUNT(DISTINCT uuid) AS EXPECT_2 FROM mtr_wsrep_notify.membership; +SELECT MAX(size) AS EXPECT_2 FROM mtr_wsrep_notify.status; +SELECT COUNT(DISTINCT idx) AS EXPECT_2 FROM mtr_wsrep_notify.status; + +# CLEANUP +DROP SCHEMA mtr_wsrep_notify; diff --git a/support-files/wsrep_notify.sh b/support-files/wsrep_notify.sh old mode 100644 new mode 100755 index bdbe3d12a39..87ba11342c5 --- a/support-files/wsrep_notify.sh +++ b/support-files/wsrep_notify.sh @@ -4,12 +4,31 @@ # It will create 'wsrep' schema and two tables in it: 'membeship' and 'status' # and fill them on every membership or node status change. # -# Edit parameters below to specify the address and login to server. - +# Edit parameters below to specify the address and login to server: +# USER=root PSWD=rootpass +# +# If these parameters are not set, then the values +# passed by the server are taken: +# HOST=127.0.0.1 PORT=3306 +# +# Edit parameters below to specify SSL parameters: +# +ssl_key= +ssl_cert= +ssl_ca= +ssl_capath= +ssl_cipher= +ssl_crl= +ssl_crlpath= +ssl_verify_server_cert=0 +# +# Client executable path: +# +CLIENT="mysql" SCHEMA="wsrep" MEMB_TABLE="$SCHEMA.membership" @@ -32,8 +51,6 @@ CREATE TABLE $STATUS_TABLE ( prim BOOLEAN /* if component is primary */ ) ENGINE=MEMORY; BEGIN; -DELETE FROM $MEMB_TABLE; -DELETE FROM $STATUS_TABLE; " END="COMMIT;" @@ -43,7 +60,7 @@ configuration_change() local idx=0 - for NODE in $(echo $MEMBERS | sed s/,/\ /g) + for NODE in $(echo "$MEMBERS" | sed s/,/\ /g) do echo "INSERT INTO $MEMB_TABLE VALUES ( $idx, " # Don't forget to properly quote string values @@ -62,17 +79,44 @@ status_update() echo "SET wsrep_on=0; BEGIN; UPDATE $STATUS_TABLE SET status='$STATUS'; COMMIT;" } +trim_string() +{ + if [ -n "${BASH_VERSION:-}" ]; then + local pattern="[![:space:]${2:-}]" + local x="${1#*$pattern}" + local z=${#1} + x=${#x} + if [ $x -ne $z ]; then + local y="${1%$pattern*}" + y=${#y} + x=$(( z-x-1 )) + y=$(( y-x+1 )) + printf '%s' "${1:$x:$y}" + else + printf '' + fi + else + local pattern="[[:space:]${2:-}]" + echo "$1" | sed -E "s/^$pattern+|$pattern+\$//g" + fi +} + COM=status_update # not a configuration change by default -while [ $# -gt 0 ] -do +STATUS="" +CLUSTER_UUID="" +PRIMARY="0" +INDEX="" +MEMBERS="" + +while [ $# -gt 0 ]; do case $1 in --status) - STATUS=$2 + STATUS=$(trim_string "$2") shift ;; --uuid) - CLUSTER_UUID=$2 + CLUSTER_UUID=$(trim_string "$2") shift ;; --primary) @@ -81,22 +125,71 @@ do shift ;; --index) - INDEX=$2 + INDEX=$(trim_string "$2") shift ;; --members) - MEMBERS=$2 + MEMBERS=$(trim_string "$2") shift ;; esac shift done -# Undefined means node is shutting down -if [ "$STATUS" != "Undefined" ] +USER=$(trim_string "$USER") +PSWD=$(trim_string "$PSWD") + +HOST=$(trim_string "$HOST") +PORT=$(trim_string "$PORT") + +case "$HOST" in +\[*) + HOST="${HOST##\[}" + HOST=$(trim_string "${HOST%%\]}") + ;; +esac + +if [ -z "$HOST" ]; then + HOST="${NOTIFY_HOST:-}" +fi +if [ -z "$PORT" ]; then + PORT="${NOTIFY_PORT:-}" +fi + +ssl_key=$(trim_string "$ssl_key"); +ssl_cert=$(trim_string "$ssl_cert"); +ssl_ca=$(trim_string "$ssl_ca"); +ssl_capath=$(trim_string "$ssl_capath"); +ssl_cipher=$(trim_string "$ssl_cipher"); +ssl_crl=$(trim_string "$ssl_crl"); +ssl_crlpath=$(trim_string "$ssl_crlpath"); +ssl_verify_server_cert=$(trim_string "$ssl_verify_server_cert"); + +SSL_PARAM="" + +if [ -n "$ssl_key" -o -n "$ssl_cert" -o \ + -n "$ssl_ca" -o -n "$ssl_capath" -o \ + -n "$ssl_cipher" ] then - $COM | mysql -B -u$USER -p$PSWD -h$HOST -P$PORT + SSL_PARAM=' --ssl' + [ -n "$ssl_key" ] && SSL_PARAM="$SSL_PARAM --ssl-key='$ssl_key'" + [ -n "$ssl_cert" ] && SSL_PARAM="$SSL_PARAM --ssl-cert='$ssl_cert'" + [ -n "$ssl_ca" ] && SSL_PARAM="$SSL_PARAM --ssl-ca='$ssl_ca'" + [ -n "$ssl_capath" ] && SSL_PARAM="$SSL_PARAM --ssl-capath='$ssl_capath'" + [ -n "$ssl_cipher" ] && SSL_PARAM="$SSL_PARAM --ssl-cipher='$ssl_cipher'" + [ -n "$ssl_crl" ] && SSL_PARAM="$SSL_PARAM --ssl-crl='$ssl_crl'" + [ -n "$ssl_crlpath" ] && SSL_PARAM="$SSL_PARAM --ssl-crlpath='$ssl_crlpath'" + if [ -n "$ssl_verify_server_cert" ]; then + if [ $ssl_verify_server_cert -ne 0 ]; then + SSL_PARAM+=' --ssl-verify-server-cert' + fi + fi +fi + +# Undefined means node is shutting down +if [ "$STATUS" != 'Undefined' ]; then + "$COM" | eval "$CLIENT" -B "-u'$USER'"${PSWD:+" -p'$PSWD'"}\ + "-h'$HOST'" "-P$PORT"$SSL_PARAM fi exit 0 -# -- cgit v1.2.1 From 1562b2c20b5b76ee305942238e3e1e66f9952e29 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Marko=20M=C3=A4kel=C3=A4?= Date: Wed, 5 Oct 2022 09:30:33 +0300 Subject: MDEV-29666 InnoDB fails to purge secondary index records when indexed virtual columns exist row_purge_get_partial(): Replaces trx_undo_rec_get_partial_row(). Also copy the purge_node_t::ref to the purge_node_t::row. In this way, the clustered index key fields will always be available, even if thanks to commit d384ead0f024995787b1f29bc672c33b0d3d40a8 (MDEV-14799) they would no longer be repeated in the remaining part of the undo log record. --- .../suite/gcol/r/innodb_virtual_debug_purge.result | 3 - .../suite/gcol/t/innodb_virtual_debug_purge.test | 3 - mysql-test/suite/innodb/r/purge_secondary.result | 15 ++ mysql-test/suite/innodb/t/purge_secondary.test | 32 ++++ storage/innobase/include/trx0rec.h | 26 +-- storage/innobase/row/row0purge.cc | 135 +++++++++++++++- storage/innobase/trx/trx0rec.cc | 176 --------------------- 7 files changed, 178 insertions(+), 212 deletions(-) diff --git a/mysql-test/suite/gcol/r/innodb_virtual_debug_purge.result b/mysql-test/suite/gcol/r/innodb_virtual_debug_purge.result index 3ef3679db75..5767aaf63ca 100644 --- a/mysql-test/suite/gcol/r/innodb_virtual_debug_purge.result +++ b/mysql-test/suite/gcol/r/innodb_virtual_debug_purge.result @@ -148,10 +148,7 @@ lock table t write; connection prevent_purge; commit; connection default; -InnoDB 0 transactions not purged disconnect lock_table; -start transaction with consistent snapshot; -commit; InnoDB 0 transactions not purged set global debug_dbug=@old_dbug; drop table t; diff --git a/mysql-test/suite/gcol/t/innodb_virtual_debug_purge.test b/mysql-test/suite/gcol/t/innodb_virtual_debug_purge.test index da203f118a8..20db2cd5533 100644 --- a/mysql-test/suite/gcol/t/innodb_virtual_debug_purge.test +++ b/mysql-test/suite/gcol/t/innodb_virtual_debug_purge.test @@ -189,10 +189,7 @@ lock table t write; connection prevent_purge; commit; connection default; ---source ../../innodb/include/wait_all_purged.inc disconnect lock_table; -start transaction with consistent snapshot; -commit; --source ../../innodb/include/wait_all_purged.inc set global debug_dbug=@old_dbug; drop table t; diff --git a/mysql-test/suite/innodb/r/purge_secondary.result b/mysql-test/suite/innodb/r/purge_secondary.result index 8f20f5baacb..66aaeb9e1a1 100644 --- a/mysql-test/suite/innodb/r/purge_secondary.result +++ b/mysql-test/suite/innodb/r/purge_secondary.result @@ -166,4 +166,19 @@ buffer_LRU_batch_evict_total_pages buffer # FLUSH TABLES t1 FOR EXPORT; # UNLOCK TABLES; DROP TABLE t1; +# +# MDEV-29666 InnoDB fails to purge secondary index records +# when indexed virtual columns exist +# +CREATE TABLE t1 (a INT, b INT, a1 INT AS(a) VIRTUAL, +INDEX(a1),INDEX(b)) ENGINE=InnoDB; +INSERT INTO t1 SET a=1, b=1; +UPDATE t1 SET a=2, b=3; +InnoDB 0 transactions not purged +FLUSH TABLE t1 FOR EXPORT; +page 4: N_RECS=0x0001 +page 5: N_RECS=0x0001 +UNLOCK TABLES; +DROP TABLE t1; +# End of 10.3 tests SET GLOBAL innodb_purge_rseg_truncate_frequency = @saved_frequency; diff --git a/mysql-test/suite/innodb/t/purge_secondary.test b/mysql-test/suite/innodb/t/purge_secondary.test index bf702b6b737..530da2c33d9 100644 --- a/mysql-test/suite/innodb/t/purge_secondary.test +++ b/mysql-test/suite/innodb/t/purge_secondary.test @@ -149,4 +149,36 @@ WHERE NAME="buffer_LRU_batch_evict_total_pages" AND COUNT > 0; DROP TABLE t1; +--echo # +--echo # MDEV-29666 InnoDB fails to purge secondary index records +--echo # when indexed virtual columns exist +--echo # + +CREATE TABLE t1 (a INT, b INT, a1 INT AS(a) VIRTUAL, +INDEX(a1),INDEX(b)) ENGINE=InnoDB; +INSERT INTO t1 SET a=1, b=1; + +UPDATE t1 SET a=2, b=3; +let DATADIR=`select @@datadir`; +let PAGE_SIZE=`select @@innodb_page_size`; + +source include/wait_all_purged.inc; +FLUSH TABLE t1 FOR EXPORT; + +perl; +my $ps = $ENV{PAGE_SIZE}; +my $file = "$ENV{DATADIR}/test/t1.ibd"; +open(FILE, "<", $file) or die "Unable to open $file\n"; +die "Unable to read $file\n" unless + sysread(FILE, $_, 6*$ps) == 6*$ps; +close(FILE); +print "page 4: N_RECS=0x", unpack("H*", substr($_, 4 * $ps + 54, 2)), "\n"; +print "page 5: N_RECS=0x", unpack("H*", substr($_, 5 * $ps + 54, 2)), "\n"; +EOF + +UNLOCK TABLES; +DROP TABLE t1; + +--echo # End of 10.3 tests + SET GLOBAL innodb_purge_rseg_truncate_frequency = @saved_frequency; diff --git a/storage/innobase/include/trx0rec.h b/storage/innobase/include/trx0rec.h index fa084ff274c..992e7645bc7 100644 --- a/storage/innobase/include/trx0rec.h +++ b/storage/innobase/include/trx0rec.h @@ -1,7 +1,7 @@ /***************************************************************************** Copyright (c) 1996, 2016, Oracle and/or its affiliates. All Rights Reserved. -Copyright (c) 2017, 2019, MariaDB Corporation. +Copyright (c) 2017, 2022, 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 @@ -136,30 +136,6 @@ trx_undo_update_rec_get_update( mem_heap_t* heap, /*!< in: memory heap from which the memory needed is allocated */ upd_t** upd); /*!< out, own: update vector */ -/*******************************************************************//** -Builds a partial row from an update undo log record, for purge. -It contains the columns which occur as ordering in any index of the table. -Any missing columns are indicated by col->mtype == DATA_MISSING. -@return pointer to remaining part of undo record */ -byte* -trx_undo_rec_get_partial_row( -/*=========================*/ - const byte* ptr, /*!< in: remaining part in update undo log - record of a suitable type, at the start of - the stored index columns; - NOTE that this copy of the undo log record must - be preserved as long as the partial row is - used, as we do NOT copy the data in the - record! */ - dict_index_t* index, /*!< in: clustered index */ - const upd_t* update, /*!< in: updated columns */ - dtuple_t** row, /*!< out, own: partial row */ - ibool ignore_prefix, /*!< in: flag to indicate if we - expect blob prefixes in undo. Used - only in the assertion. */ - mem_heap_t* heap) /*!< in: memory heap from which the memory - needed is allocated */ - MY_ATTRIBUTE((nonnull, warn_unused_result)); /** Report a RENAME TABLE operation. @param[in,out] trx transaction @param[in] table table that is being renamed diff --git a/storage/innobase/row/row0purge.cc b/storage/innobase/row/row0purge.cc index e46d515e8c2..77e772786d5 100644 --- a/storage/innobase/row/row0purge.cc +++ b/storage/innobase/row/row0purge.cc @@ -1,7 +1,7 @@ /***************************************************************************** Copyright (c) 1997, 2017, Oracle and/or its affiliates. All Rights Reserved. -Copyright (c) 2017, 2021, MariaDB Corporation. +Copyright (c) 2017, 2022, 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 @@ -1004,6 +1004,134 @@ skip_secondaries: row_purge_upd_exist_or_extern_func(node,undo_rec) #endif /* UNIV_DEBUG */ +/** Build a partial row from an update undo log record for purge. +Any columns which occur as ordering in any index of the table are present. +Any missing columns are indicated by col->mtype == DATA_MISSING. + +@param ptr remaining part of the undo log record +@param index clustered index +@param node purge node +@return pointer to remaining part of undo record */ +static byte *row_purge_get_partial(const byte *ptr, const dict_index_t &index, + purge_node_t *node) +{ + bool first_v_col= true; + bool is_undo_log= true; + + ut_ad(index.is_primary()); + ut_ad(index.n_uniq == node->ref->n_fields); + + node->row= dtuple_create_with_vcol(node->heap, index.table->n_cols, + index.table->n_v_cols); + + /* Mark all columns in the row uninitialized, so that + we can distinguish missing fields from fields that are SQL NULL. */ + for (ulint i= 0; i < index.table->n_cols; i++) + node->row->fields[i].type.mtype= DATA_MISSING; + + dtuple_init_v_fld(node->row); + + for (const upd_field_t *uf= node->update->fields, *const ue= + node->update->fields + node->update->n_fields; uf != ue; uf++) + if (!uf->old_v_val) + node->row->fields[dict_index_get_nth_col(&index, uf->field_no)->ind]= + uf->new_val; + + const byte *end_ptr= ptr + mach_read_from_2(ptr); + ptr+= 2; + + while (ptr != end_ptr) + { + dfield_t *dfield; + const byte *field; + const dict_col_t *col; + ulint len; + ulint orig_len; + + ulint field_no= mach_read_next_compressed(&ptr); + + if (field_no >= REC_MAX_N_FIELDS) + { + ptr= trx_undo_read_v_idx(index.table, ptr, first_v_col, &is_undo_log, + &field_no); + first_v_col= false; + + ptr= trx_undo_rec_get_col_val(ptr, &field, &len, &orig_len); + + if (field_no == ULINT_UNDEFINED) + continue; /* there no longer is an index on the virtual column */ + + dict_v_col_t *vcol= dict_table_get_nth_v_col(index.table, field_no); + col =&vcol->m_col; + dfield= dtuple_get_nth_v_field(node->row, vcol->v_pos); + dict_col_copy_type(&vcol->m_col, &dfield->type); + } + else + { + ptr= trx_undo_rec_get_col_val(ptr, &field, &len, &orig_len); + col= dict_index_get_nth_col(&index, field_no); + dfield= dtuple_get_nth_field(node->row, col->ind); + ut_ad(dfield->type.mtype == DATA_MISSING || + dict_col_type_assert_equal(col, &dfield->type)); + ut_ad(dfield->type.mtype == DATA_MISSING || + dfield->len == len || + (len != UNIV_SQL_NULL && len >= UNIV_EXTERN_STORAGE_FIELD)); + dict_col_copy_type(dict_table_get_nth_col(index.table, col->ind), + &dfield->type); + } + + dfield_set_data(dfield, field, len); + + if (len == UNIV_SQL_NULL || len < UNIV_EXTERN_STORAGE_FIELD) + continue; + + spatial_status_t spatial_status= static_cast + ((len & SPATIAL_STATUS_MASK) >> SPATIAL_STATUS_SHIFT); + len&= ~SPATIAL_STATUS_MASK; + + /* Keep compatible with 5.7.9 format. */ + if (spatial_status == SPATIAL_UNKNOWN) + spatial_status= dict_col_get_spatial_status(col); + + switch (UNIV_EXPECT(spatial_status, SPATIAL_NONE)) { + case SPATIAL_ONLY: + ut_ad(len - UNIV_EXTERN_STORAGE_FIELD == DATA_MBR_LEN); + dfield_set_len(dfield, len - UNIV_EXTERN_STORAGE_FIELD); + break; + + case SPATIAL_MIXED: + dfield_set_len(dfield, len - UNIV_EXTERN_STORAGE_FIELD - DATA_MBR_LEN); + break; + + default: + dfield_set_len(dfield, len - UNIV_EXTERN_STORAGE_FIELD); + break; + } + + dfield_set_ext(dfield); + dfield_set_spatial_status(dfield, spatial_status); + + if (!col->ord_part || spatial_status == SPATIAL_ONLY || + node->rec_type == TRX_UNDO_UPD_DEL_REC) + continue; + /* If the prefix of this BLOB column is indexed, ensure that enough + prefix is stored in the undo log record. */ + ut_a(dfield_get_len(dfield) >= BTR_EXTERN_FIELD_REF_SIZE); + ut_a(dict_table_has_atomic_blobs(index.table) || + dfield_get_len(dfield) >= + REC_ANTELOPE_MAX_INDEX_COL_LEN + BTR_EXTERN_FIELD_REF_SIZE); + } + + for (ulint i= 0; i < index.n_uniq; i++) + { + dfield_t &field= node->row->fields[index.fields[i].col->ind]; + if (field.type.mtype == DATA_MISSING) + field= node->ref->fields[i]; + } + + return const_cast(ptr); +} + /***********************************************************//** Parses the row reference and other info in a modify undo log record. @return true if purge operation required */ @@ -1153,10 +1281,7 @@ err_exit: if (!(node->cmpl_info & UPD_NODE_NO_ORD_CHANGE)) { ut_ad(!(node->update->info_bits & REC_INFO_MIN_REC_FLAG)); - ptr = trx_undo_rec_get_partial_row( - ptr, clust_index, node->update, &node->row, - type == TRX_UNDO_UPD_DEL_REC, - node->heap); + ptr = row_purge_get_partial(ptr, *clust_index, node); } else if (node->update->info_bits & REC_INFO_MIN_REC_FLAG) { node->ref = &trx_undo_metadata; } diff --git a/storage/innobase/trx/trx0rec.cc b/storage/innobase/trx/trx0rec.cc index d7ec2a38f19..e25ebc3e22a 100644 --- a/storage/innobase/trx/trx0rec.cc +++ b/storage/innobase/trx/trx0rec.cc @@ -1655,182 +1655,6 @@ trx_undo_update_rec_get_update( return(const_cast(ptr)); } -/*******************************************************************//** -Builds a partial row from an update undo log record, for purge. -It contains the columns which occur as ordering in any index of the table. -Any missing columns are indicated by col->mtype == DATA_MISSING. -@return pointer to remaining part of undo record */ -byte* -trx_undo_rec_get_partial_row( -/*=========================*/ - const byte* ptr, /*!< in: remaining part in update undo log - record of a suitable type, at the start of - the stored index columns; - NOTE that this copy of the undo log record must - be preserved as long as the partial row is - used, as we do NOT copy the data in the - record! */ - dict_index_t* index, /*!< in: clustered index */ - const upd_t* update, /*!< in: updated columns */ - dtuple_t** row, /*!< out, own: partial row */ - ibool ignore_prefix, /*!< in: flag to indicate if we - expect blob prefixes in undo. Used - only in the assertion. */ - mem_heap_t* heap) /*!< in: memory heap from which the memory - needed is allocated */ -{ - const byte* end_ptr; - bool first_v_col = true; - bool is_undo_log = true; - - ut_ad(index->is_primary()); - - *row = dtuple_create_with_vcol( - heap, dict_table_get_n_cols(index->table), - dict_table_get_n_v_cols(index->table)); - - /* Mark all columns in the row uninitialized, so that - we can distinguish missing fields from fields that are SQL NULL. */ - for (ulint i = 0; i < dict_table_get_n_cols(index->table); i++) { - dfield_get_type(dtuple_get_nth_field(*row, i)) - ->mtype = DATA_MISSING; - } - - dtuple_init_v_fld(*row); - - for (const upd_field_t* uf = update->fields, * const ue - = update->fields + update->n_fields; - uf != ue; uf++) { - if (uf->old_v_val) { - continue; - } - ulint c = dict_index_get_nth_col(index, uf->field_no)->ind; - *dtuple_get_nth_field(*row, c) = uf->new_val; - } - - end_ptr = ptr + mach_read_from_2(ptr); - ptr += 2; - - while (ptr != end_ptr) { - dfield_t* dfield; - const byte* field; - ulint field_no; - const dict_col_t* col; - ulint col_no; - ulint len; - ulint orig_len; - bool is_virtual; - - field_no = mach_read_next_compressed(&ptr); - - is_virtual = (field_no >= REC_MAX_N_FIELDS); - - if (is_virtual) { - ptr = trx_undo_read_v_idx( - index->table, ptr, first_v_col, &is_undo_log, - &field_no); - first_v_col = false; - } - - ptr = trx_undo_rec_get_col_val(ptr, &field, &len, &orig_len); - - /* This column could be dropped or no longer indexed */ - if (field_no == ULINT_UNDEFINED) { - ut_ad(is_virtual); - continue; - } - - if (is_virtual) { - dict_v_col_t* vcol = dict_table_get_nth_v_col( - index->table, field_no); - col = &vcol->m_col; - col_no = dict_col_get_no(col); - dfield = dtuple_get_nth_v_field(*row, vcol->v_pos); - dict_col_copy_type( - &vcol->m_col, - dfield_get_type(dfield)); - } else { - col = dict_index_get_nth_col(index, field_no); - col_no = dict_col_get_no(col); - dfield = dtuple_get_nth_field(*row, col_no); - ut_ad(dfield->type.mtype == DATA_MISSING - || dict_col_type_assert_equal(col, - &dfield->type)); - ut_ad(dfield->type.mtype == DATA_MISSING - || dfield->len == len - || (len != UNIV_SQL_NULL - && len >= UNIV_EXTERN_STORAGE_FIELD)); - dict_col_copy_type( - dict_table_get_nth_col(index->table, col_no), - dfield_get_type(dfield)); - } - - dfield_set_data(dfield, field, len); - - if (len != UNIV_SQL_NULL - && len >= UNIV_EXTERN_STORAGE_FIELD) { - spatial_status_t spatial_status; - - /* Decode spatial status. */ - spatial_status = static_cast( - (len & SPATIAL_STATUS_MASK) - >> SPATIAL_STATUS_SHIFT); - len &= ~SPATIAL_STATUS_MASK; - - /* Keep compatible with 5.7.9 format. */ - if (spatial_status == SPATIAL_UNKNOWN) { - spatial_status = - dict_col_get_spatial_status(col); - } - - switch (spatial_status) { - case SPATIAL_ONLY: - ut_ad(len - UNIV_EXTERN_STORAGE_FIELD - == DATA_MBR_LEN); - dfield_set_len( - dfield, - len - UNIV_EXTERN_STORAGE_FIELD); - break; - - case SPATIAL_MIXED: - dfield_set_len( - dfield, - len - UNIV_EXTERN_STORAGE_FIELD - - DATA_MBR_LEN); - break; - - case SPATIAL_NONE: - dfield_set_len( - dfield, - len - UNIV_EXTERN_STORAGE_FIELD); - break; - - case SPATIAL_UNKNOWN: - ut_ad(0); - break; - } - - dfield_set_ext(dfield); - dfield_set_spatial_status(dfield, spatial_status); - - /* If the prefix of this column is indexed, - ensure that enough prefix is stored in the - undo log record. */ - if (!ignore_prefix && col->ord_part - && spatial_status != SPATIAL_ONLY) { - ut_a(dfield_get_len(dfield) - >= BTR_EXTERN_FIELD_REF_SIZE); - ut_a(dict_table_has_atomic_blobs(index->table) - || dfield_get_len(dfield) - >= REC_ANTELOPE_MAX_INDEX_COL_LEN - + BTR_EXTERN_FIELD_REF_SIZE); - } - } - } - - return(const_cast(ptr)); -} - /** Erase the unused undo log page end. @param[in,out] undo_page undo log page @return whether the page contained something */ -- cgit v1.2.1 From df97eb1432f91ad13e562111bda393b3650719d0 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Marko=20M=C3=A4kel=C3=A4?= Date: Wed, 5 Oct 2022 10:09:49 +0300 Subject: Remove HAVE_SNPRINTF This fixes up commit 77c184df7c056da7364e606ac977cc2d3cd826ad which explicitly specifies that we use ISO/IEC 9899:1999 (C99), which includes the snprintf() function. --- client/mysqlimport.c | 6 +----- config.h.cmake | 1 - configure.cmake | 1 - sql/sql_analyse.cc | 4 ---- storage/maria/maria_ftdump.c | 4 ---- storage/myisam/myisam_ftdump.c | 4 ---- 6 files changed, 1 insertion(+), 19 deletions(-) diff --git a/client/mysqlimport.c b/client/mysqlimport.c index c5c1554ca6a..ac0ad793c3f 100644 --- a/client/mysqlimport.c +++ b/client/mysqlimport.c @@ -1,6 +1,6 @@ /* Copyright (c) 2000, 2015, Oracle and/or its affiliates. - Copyright (c) 2011, 2017, MariaDB + Copyright (c) 2011, 2022, MariaDB This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by @@ -323,11 +323,7 @@ static int write_to_table(char *filename, MYSQL *mysql) { if (verbose) fprintf(stdout, "Deleting the old data from table %s\n", tablename); -#ifdef HAVE_SNPRINTF snprintf(sql_statement, FN_REFLEN*16+256, "DELETE FROM %s", tablename); -#else - sprintf(sql_statement, "DELETE FROM %s", tablename); -#endif if (mysql_query(mysql, sql_statement)) { db_error_with_table(mysql, tablename); diff --git a/config.h.cmake b/config.h.cmake index 3a4a030fd59..e7754337b1f 100644 --- a/config.h.cmake +++ b/config.h.cmake @@ -224,7 +224,6 @@ #cmakedefine HAVE_SIGWAIT 1 #cmakedefine HAVE_SIGWAITINFO 1 #cmakedefine HAVE_SLEEP 1 -#cmakedefine HAVE_SNPRINTF 1 #cmakedefine HAVE_STPCPY 1 #cmakedefine HAVE_STRERROR 1 #cmakedefine HAVE_STRCOLL 1 diff --git a/configure.cmake b/configure.cmake index a899c2fd671..475fd250329 100644 --- a/configure.cmake +++ b/configure.cmake @@ -407,7 +407,6 @@ CHECK_FUNCTION_EXISTS (sigwait HAVE_SIGWAIT) CHECK_FUNCTION_EXISTS (sigwaitinfo HAVE_SIGWAITINFO) CHECK_FUNCTION_EXISTS (sigset HAVE_SIGSET) CHECK_FUNCTION_EXISTS (sleep HAVE_SLEEP) -CHECK_FUNCTION_EXISTS (snprintf HAVE_SNPRINTF) CHECK_FUNCTION_EXISTS (stpcpy HAVE_STPCPY) CHECK_FUNCTION_EXISTS (strcoll HAVE_STRCOLL) CHECK_FUNCTION_EXISTS (strerror HAVE_STRERROR) diff --git a/sql/sql_analyse.cc b/sql/sql_analyse.cc index 61474433506..8e833035b96 100644 --- a/sql/sql_analyse.cc +++ b/sql/sql_analyse.cc @@ -415,13 +415,9 @@ void field_real::add() } else { -#ifdef HAVE_SNPRINTF buff[sizeof(buff)-1]=0; // Safety snprintf(buff, sizeof(buff)-1, "%-.*f", (int) decs, num); length = (uint) strlen(buff); -#else - length= snprintf(buff, sizeof(buff), "%-.*f", (int) decs, num); -#endif // We never need to check further than this end = buff + length - 1 - decs + max_notzero_dec_len; diff --git a/storage/maria/maria_ftdump.c b/storage/maria/maria_ftdump.c index 75ff9bd2642..1a7e1cda59f 100644 --- a/storage/maria/maria_ftdump.c +++ b/storage/maria/maria_ftdump.c @@ -119,11 +119,7 @@ int main(int argc,char *argv[]) if (subkeys.i >= 0) weight= subkeys.f; -#ifdef HAVE_SNPRINTF snprintf(buf,MAX_LEN,"%.*s",(int) keylen,info->lastkey_buff+1); -#else - sprintf(buf,"%.*s",(int) keylen,info->lastkey_buff+1); -#endif my_casedn_str(default_charset_info,buf); total++; lengths[keylen]++; diff --git a/storage/myisam/myisam_ftdump.c b/storage/myisam/myisam_ftdump.c index 7ced701ed5b..2d96a951890 100644 --- a/storage/myisam/myisam_ftdump.c +++ b/storage/myisam/myisam_ftdump.c @@ -117,11 +117,7 @@ int main(int argc,char *argv[]) if (subkeys.i >= 0) weight= subkeys.f; -#ifdef HAVE_SNPRINTF snprintf(buf,MAX_LEN,"%.*s",(int) keylen,info->lastkey+1); -#else - sprintf(buf,"%.*s",(int) keylen,info->lastkey+1); -#endif my_casedn_str(default_charset_info,buf); total++; lengths[keylen]++; -- cgit v1.2.1 From c64e2d60a39573827b49e6d57a0812b092e605b8 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Marko=20M=C3=A4kel=C3=A4?= Date: Wed, 5 Oct 2022 15:15:28 +0300 Subject: MDEV-29710: Disable innodb.table_flags under Valgrind --- mysql-test/suite/innodb/t/table_flags.test | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/mysql-test/suite/innodb/t/table_flags.test b/mysql-test/suite/innodb/t/table_flags.test index 13e1fc01dc0..9d417909533 100644 --- a/mysql-test/suite/innodb/t/table_flags.test +++ b/mysql-test/suite/innodb/t/table_flags.test @@ -2,6 +2,12 @@ # Embedded server tests do not support restarting --source include/not_embedded.inc --source include/maybe_debug.inc +# Slow shutdown may take more than 120 seconds under Valgrind, +# causing the server to be (silently) killed. +# Due to that, crash recovery could "heal" the damage that our +# Perl code is inflicting, and the SELECT statements could succeed +# instead of failing with ER_NO_SUCH_TABLE_IN_ENGINE. +--source include/not_valgrind.inc --disable_query_log call mtr.add_suppression("InnoDB: Table `mysql`\\.`innodb_table_stats` not found"); -- cgit v1.2.1 From 380e06f84bbed5684a8f27c2c8fc9ea99b846ae6 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Marko=20M=C3=A4kel=C3=A4?= Date: Wed, 5 Oct 2022 15:16:03 +0300 Subject: MDEV-29710: Disable sys_vars.innodb_flush_method_func under Valgrind The test could emit some I/O error when run under Valgrind. --- mysql-test/suite/sys_vars/t/innodb_flush_method_func.test | 2 ++ 1 file changed, 2 insertions(+) diff --git a/mysql-test/suite/sys_vars/t/innodb_flush_method_func.test b/mysql-test/suite/sys_vars/t/innodb_flush_method_func.test index aad91d0f4a3..7293a99db41 100644 --- a/mysql-test/suite/sys_vars/t/innodb_flush_method_func.test +++ b/mysql-test/suite/sys_vars/t/innodb_flush_method_func.test @@ -1,6 +1,8 @@ --source include/have_innodb.inc # Embedded server tests do not support restarting. --source include/not_embedded.inc +# InnoDB: Cannot read first page of './ibdata1' I/O error +--source include/not_valgrind.inc call mtr.add_suppression("InnoDB: Failed to set .*DIRECT"); --replace_result unbuffered fsync -- cgit v1.2.1 From e0bcff10ef3984ae2354a52fb5f4cfa2c9e6efa0 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Marko=20M=C3=A4kel=C3=A4?= Date: Wed, 5 Oct 2022 15:18:44 +0300 Subject: MDEV-29710: Disable main.log_slow under Valgrind Under Valgrind, this test may occasionally fail because the sleep-based timeouts of less than 1 second could be exceeded. --- mysql-test/main/log_slow.test | 2 ++ 1 file changed, 2 insertions(+) diff --git a/mysql-test/main/log_slow.test b/mysql-test/main/log_slow.test index 64fd8202985..b51777d859e 100644 --- a/mysql-test/main/log_slow.test +++ b/mysql-test/main/log_slow.test @@ -1,3 +1,5 @@ +--source include/no_valgrind_without_big.inc + # # Testing of slow log query options # -- cgit v1.2.1 From 111cbdf3dae9c5f8e256db21c83307e5477055b8 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Marko=20M=C3=A4kel=C3=A4?= Date: Wed, 5 Oct 2022 15:18:58 +0300 Subject: MDEV-29710: Valgrind tests massively fail due to silently killing server on shutdown timeout Let us disable Valgrind on tests that would fail because a server shutdown or a STOP SLAVE command would take longer, causing the test harness to forcibly and silently kill the server due to an exceeded timeout. --- mysql-test/include/master-slave.inc | 2 ++ mysql-test/main/mysql_upgrade.test | 1 + mysql-test/main/plugin_auth.test | 1 + mysql-test/suite/innodb/t/alter_missing_tablespace.test | 1 + mysql-test/suite/innodb/t/ibuf_not_empty.test | 1 + mysql-test/suite/innodb/t/innodb-get-fk.test | 2 ++ mysql-test/suite/innodb/t/missing_tablespaces.test | 1 + mysql-test/suite/innodb/t/xa_recovery.test | 1 + mysql-test/suite/mariabackup/log_page_corruption.test | 1 + mysql-test/suite/rpl/t/rpl_gtid_stop_start.test | 1 + mysql-test/suite/rpl/t/rpl_mdev12179.test | 1 + .../suite/sys_vars/t/innodb_buffer_pool_dump_at_shutdown_basic.test | 1 + 12 files changed, 14 insertions(+) diff --git a/mysql-test/include/master-slave.inc b/mysql-test/include/master-slave.inc index 9ed206b2c22..5b603fbfdb3 100644 --- a/mysql-test/include/master-slave.inc +++ b/mysql-test/include/master-slave.inc @@ -1,3 +1,5 @@ +--source include/no_valgrind_without_big.inc + # ==== Purpose ==== # # Configure two servers to be replication master and slave. diff --git a/mysql-test/main/mysql_upgrade.test b/mysql-test/main/mysql_upgrade.test index 0e42bb81fd9..67ec8de70d9 100644 --- a/mysql-test/main/mysql_upgrade.test +++ b/mysql-test/main/mysql_upgrade.test @@ -2,6 +2,7 @@ -- source include/have_working_dns.inc -- source include/have_innodb.inc -- source include/have_partition.inc +-- source include/no_valgrind_without_big.inc set sql_mode=""; diff --git a/mysql-test/main/plugin_auth.test b/mysql-test/main/plugin_auth.test index 1700a755492..0fde2953352 100644 --- a/mysql-test/main/plugin_auth.test +++ b/mysql-test/main/plugin_auth.test @@ -2,6 +2,7 @@ --source include/not_embedded.inc --source include/mysql_upgrade_preparation.inc --source include/have_innodb.inc +--source include/no_valgrind_without_big.inc SET GLOBAL SQL_MODE=""; SET LOCAL SQL_MODE=""; diff --git a/mysql-test/suite/innodb/t/alter_missing_tablespace.test b/mysql-test/suite/innodb/t/alter_missing_tablespace.test index c1cfc0fa092..20088ef9dd3 100644 --- a/mysql-test/suite/innodb/t/alter_missing_tablespace.test +++ b/mysql-test/suite/innodb/t/alter_missing_tablespace.test @@ -1,5 +1,6 @@ --source include/not_embedded.inc --source include/innodb_page_size.inc +--source include/no_valgrind_without_big.inc --echo # --echo # Bug#13955083 ALLOW IN-PLACE DDL OPERATIONS ON MISSING diff --git a/mysql-test/suite/innodb/t/ibuf_not_empty.test b/mysql-test/suite/innodb/t/ibuf_not_empty.test index 43f09bf6828..72b57fd48ad 100644 --- a/mysql-test/suite/innodb/t/ibuf_not_empty.test +++ b/mysql-test/suite/innodb/t/ibuf_not_empty.test @@ -5,6 +5,7 @@ --source include/not_embedded.inc # The test is not big enough to use change buffering with larger page size. --source include/have_innodb_max_16k.inc +--source include/no_valgrind_without_big.inc SET GLOBAL innodb_purge_rseg_truncate_frequency=1; --disable_query_log diff --git a/mysql-test/suite/innodb/t/innodb-get-fk.test b/mysql-test/suite/innodb/t/innodb-get-fk.test index 47db92a0c6d..b4b170b89f9 100644 --- a/mysql-test/suite/innodb/t/innodb-get-fk.test +++ b/mysql-test/suite/innodb/t/innodb-get-fk.test @@ -2,6 +2,8 @@ --source include/default_charset.inc # need to restart server --source include/not_embedded.inc +--source include/no_valgrind_without_big.inc + CREATE SCHEMA `repro`; CREATE TABLE `repro`.`crew` ( diff --git a/mysql-test/suite/innodb/t/missing_tablespaces.test b/mysql-test/suite/innodb/t/missing_tablespaces.test index 98efc51d7b8..8dc560e8a07 100644 --- a/mysql-test/suite/innodb/t/missing_tablespaces.test +++ b/mysql-test/suite/innodb/t/missing_tablespaces.test @@ -4,6 +4,7 @@ --source include/not_embedded.inc #Windows has trouble creating files/directories with long names --source include/not_windows.inc +--source include/no_valgrind_without_big.inc --echo # --echo # Bug#19419026 WHEN A TABLESPACE IS NOT FOUND, DO NOT REPORT "TABLE NOT FOUND" diff --git a/mysql-test/suite/innodb/t/xa_recovery.test b/mysql-test/suite/innodb/t/xa_recovery.test index bb8e3316860..f0fbb1a94c3 100644 --- a/mysql-test/suite/innodb/t/xa_recovery.test +++ b/mysql-test/suite/innodb/t/xa_recovery.test @@ -1,6 +1,7 @@ --source include/have_innodb.inc # Embedded server does not support restarting. --source include/not_embedded.inc +--source include/no_valgrind_without_big.inc # MDEV-8841 - close tables opened by previous tests, # so they don't get marked crashed when the server gets crashed diff --git a/mysql-test/suite/mariabackup/log_page_corruption.test b/mysql-test/suite/mariabackup/log_page_corruption.test index 0151afb96b4..e14735fd024 100644 --- a/mysql-test/suite/mariabackup/log_page_corruption.test +++ b/mysql-test/suite/mariabackup/log_page_corruption.test @@ -1,4 +1,5 @@ --source include/have_debug.inc +--source include/no_valgrind_without_big.inc --echo ######## --echo # Test for generating "innodb_corrupted_pages" file during full and diff --git a/mysql-test/suite/rpl/t/rpl_gtid_stop_start.test b/mysql-test/suite/rpl/t/rpl_gtid_stop_start.test index 4202aa82516..75f9b5e479a 100644 --- a/mysql-test/suite/rpl/t/rpl_gtid_stop_start.test +++ b/mysql-test/suite/rpl/t/rpl_gtid_stop_start.test @@ -1,6 +1,7 @@ --let $rpl_topology=1->2 --source include/rpl_init.inc --source include/have_innodb.inc +--source include/no_valgrind_without_big.inc --echo *** Test normal shutdown/restart of slave server configured as a GTID slave. *** diff --git a/mysql-test/suite/rpl/t/rpl_mdev12179.test b/mysql-test/suite/rpl/t/rpl_mdev12179.test index a0241784c85..f89f87abe28 100644 --- a/mysql-test/suite/rpl/t/rpl_mdev12179.test +++ b/mysql-test/suite/rpl/t/rpl_mdev12179.test @@ -1,6 +1,7 @@ --source include/have_innodb.inc --let $rpl_topology=1->2 --source include/rpl_init.inc +--source include/no_valgrind_without_big.inc --connection server_2 call mtr.add_suppression("The automatically created table.*name may not be entirely in lowercase"); diff --git a/mysql-test/suite/sys_vars/t/innodb_buffer_pool_dump_at_shutdown_basic.test b/mysql-test/suite/sys_vars/t/innodb_buffer_pool_dump_at_shutdown_basic.test index feb7bf05638..072d1cec1a4 100644 --- a/mysql-test/suite/sys_vars/t/innodb_buffer_pool_dump_at_shutdown_basic.test +++ b/mysql-test/suite/sys_vars/t/innodb_buffer_pool_dump_at_shutdown_basic.test @@ -5,6 +5,7 @@ -- source include/have_innodb.inc # include/restart_mysqld.inc does not work in embedded mode -- source include/not_embedded.inc +-- source include/no_valgrind_without_big.inc # Check the default value SET @orig = @@global.innodb_buffer_pool_dump_at_shutdown; -- cgit v1.2.1 From c0eda62aec1de8b74ca51791df5ad142dee2ef08 Mon Sep 17 00:00:00 2001 From: Vlad Lesin Date: Wed, 31 Aug 2022 17:49:38 +0300 Subject: MDEV-27927 row_sel_try_search_shortcut_for_mysql() does not latch a page, violating read view isolation btr_search_guess_on_hash() would only acquire an index page latch if it is invoked with ahi_latch=NULL. If it's invoked from row_sel_try_search_shortcut_for_mysql() with ahi_latch!=NULL, a page will not be latched, and row_search_mvcc() will get a pointer to the record, which can be changed by some other transaction before the record was stored in result buffer with row_sel_store_mysql_rec() call. ahi_latch argument of btr_cur_search_to_nth_level_func() and btr_pcur_open_with_no_init_func() is used only for row_sel_try_search_shortcut_for_mysql(). btr_cur_search_to_nth_level_func(..., ahi_latch !=0, ...) is invoked only from btr_pcur_open_with_no_init_func(..., ahi_latch !=0, ...), which, in turns, is invoked only from row_sel_try_search_shortcut_for_mysql(). I suppose that separate case with ahi_latch!=0 was intentionally implemented to protect row_sel_store_mysql_rec() call in row_search_mvcc() just after row_sel_try_search_shortcut_for_mysql() call. After the ahi_latch was moved from row_seach_mvcc() to row_sel_try_search_shortcut_for_mysql(), there is no need in it at all if btr_search_guess_on_hash() latches a page unconditionally. And if btr_search_guess_on_hash() latched the page, any access to the record in row_sel_try_search_shortcut_for_mysql() after btr_pcur_open_with_no_init() call will be protected with the page latch. The fix is to remove ahi_latch argument from btr_pcur_open_with_no_init_func(), btr_cur_search_to_nth_level_func() and btr_search_guess_on_hash(). There will not be test, as to test it we need to freeze some SELECT execution in the point between row_sel_try_search_shortcut_for_mysql() and row_sel_store_mysql_rec() calls in row_search_mvcc(), and to change the record in some other transaction to let row_sel_store_mysql_rec() to store changed record in result buffer. Buf we can't do this with the fix, as the page will be latched in btr_search_guess_on_hash() call. --- storage/innobase/btr/btr0btr.cc | 6 +-- storage/innobase/btr/btr0cur.cc | 86 ++++++++++++++--------------------- storage/innobase/btr/btr0pcur.cc | 6 +-- storage/innobase/btr/btr0sea.cc | 59 ++++++++---------------- storage/innobase/buf/buf0buf.cc | 22 ++------- storage/innobase/dict/dict0dict.cc | 4 +- storage/innobase/fts/fts0fts.cc | 4 +- storage/innobase/gis/gis0sea.cc | 8 ++-- storage/innobase/include/btr0cur.h | 77 +++++++++++++------------------ storage/innobase/include/btr0pcur.h | 55 +++++++++------------- storage/innobase/include/btr0pcur.inl | 58 ++++++++++------------- storage/innobase/include/btr0sea.h | 1 - storage/innobase/row/row0ins.cc | 10 ++-- storage/innobase/row/row0log.cc | 6 +-- storage/innobase/row/row0merge.cc | 7 ++- storage/innobase/row/row0sel.cc | 18 ++------ 16 files changed, 160 insertions(+), 267 deletions(-) diff --git a/storage/innobase/btr/btr0btr.cc b/storage/innobase/btr/btr0btr.cc index 2bba68f0f37..f041e35e501 100644 --- a/storage/innobase/btr/btr0btr.cc +++ b/storage/innobase/btr/btr0btr.cc @@ -876,7 +876,7 @@ btr_page_get_father_node_ptr_func( err = btr_cur_search_to_nth_level( index, level + 1, tuple, - PAGE_CUR_LE, latch_mode, cursor, 0, + PAGE_CUR_LE, latch_mode, cursor, file, line, mtr); if (err != DB_SUCCESS) { @@ -2380,7 +2380,7 @@ btr_insert_on_non_leaf_level_func( dberr_t err = btr_cur_search_to_nth_level( index, level, tuple, PAGE_CUR_LE, BTR_CONT_MODIFY_TREE, - &cursor, 0, file, line, mtr); + &cursor, file, line, mtr); if (err != DB_SUCCESS) { ib::warn() << " Error code: " << err @@ -2401,7 +2401,7 @@ btr_insert_on_non_leaf_level_func( btr_cur_search_to_nth_level(index, level, tuple, PAGE_CUR_RTREE_INSERT, BTR_CONT_MODIFY_TREE, - &cursor, 0, file, line, mtr); + &cursor, file, line, mtr); } ut_ad(cursor.flag == BTR_CUR_BINARY); diff --git a/storage/innobase/btr/btr0cur.cc b/storage/innobase/btr/btr0cur.cc index 95ac5db4e70..8788094ec0a 100644 --- a/storage/innobase/btr/btr0cur.cc +++ b/storage/innobase/btr/btr0cur.cc @@ -1102,38 +1102,36 @@ If mode is PAGE_CUR_GE, then up_match will a have a sensible value. If mode is PAGE_CUR_LE , cursor is left at the place where an insert of the search tuple should be performed in the B-tree. InnoDB does an insert immediately after the cursor. Thus, the cursor may end up on a user record, -or on a page infimum record. */ -dberr_t -btr_cur_search_to_nth_level_func( - dict_index_t* index, /*!< in: index */ - ulint level, /*!< in: the tree level of search */ - const dtuple_t* tuple, /*!< in: data tuple; NOTE: n_fields_cmp in - tuple must be set so that it cannot get - compared to the node ptr page number field! */ - page_cur_mode_t mode, /*!< in: PAGE_CUR_L, ...; - Inserts should always be made using - PAGE_CUR_LE to search the position! */ - ulint latch_mode, /*!< in: BTR_SEARCH_LEAF, ..., ORed with - at most one of BTR_INSERT, BTR_DELETE_MARK, - BTR_DELETE, or BTR_ESTIMATE; - cursor->left_block is used to store a pointer - to the left neighbor page, in the cases - BTR_SEARCH_PREV and BTR_MODIFY_PREV; - NOTE that if ahi_latch, we might not have a - cursor page latch, we assume that ahi_latch - protects the record! */ - btr_cur_t* cursor, /*!< in/out: tree cursor; the cursor page is - s- or x-latched, but see also above! */ -#ifdef BTR_CUR_HASH_ADAPT - rw_lock_t* ahi_latch, - /*!< in: currently held btr_search_latch - (in RW_S_LATCH mode), or NULL */ -#endif /* BTR_CUR_HASH_ADAPT */ - const char* file, /*!< in: file name */ - unsigned line, /*!< in: line where called */ - mtr_t* mtr, /*!< in: mtr */ - ib_uint64_t autoinc)/*!< in: PAGE_ROOT_AUTO_INC to be written - (0 if none) */ +or on a page infimum record. +@param index index +@param level the tree level of search +@param tuple data tuple; NOTE: n_fields_cmp in tuple must be set so that + it cannot get compared to the node ptr page number field! +@param mode PAGE_CUR_L, NOTE that if the search is made using a unique + prefix of a record, mode should be PAGE_CUR_LE, not + PAGE_CUR_GE, as the latter may end up on the previous page of + the record! Inserts should always be made using PAGE_CUR_LE + to search the position! +@param latch_mode BTR_SEARCH_LEAF, ..., ORed with at most one of BTR_INSERT, + BTR_DELETE_MARK, BTR_DELETE, or BTR_ESTIMATE; + cursor->left_block is used to store a pointer to the left + neighbor page, in the cases BTR_SEARCH_PREV and + BTR_MODIFY_PREV; NOTE that if ahi_latch, we might not have a + cursor page latch, we assume that ahi_latch protects the + record! +@param cursor tree cursor; the cursor page is s- or x-latched, but see also + above! +@param file file name +@param line line where called +@param mtr mini-transaction +@param autoinc PAGE_ROOT_AUTO_INC to be written (0 if none) +@return DB_SUCCESS on success or error code otherwise */ +dberr_t btr_cur_search_to_nth_level(dict_index_t *index, ulint level, + const dtuple_t *tuple, + page_cur_mode_t mode, ulint latch_mode, + btr_cur_t *cursor, const char *file, + unsigned line, mtr_t *mtr, + ib_uint64_t autoinc) { page_t* page = NULL; /* remove warning */ buf_block_t* block; @@ -1301,15 +1299,14 @@ btr_cur_search_to_nth_level_func( && mode != PAGE_CUR_LE_OR_EXTENDS # endif /* PAGE_CUR_LE_OR_EXTENDS */ && !dict_index_is_spatial(index) - /* If !ahi_latch, we do a dirty read of + /* We do a dirty read of btr_search_enabled below, and btr_search_guess_on_hash() will have to check it again. */ && btr_search_enabled && !modify_external && !(tuple->info_bits & REC_INFO_MIN_REC_FLAG) && btr_search_guess_on_hash(index, info, tuple, mode, - latch_mode, cursor, - ahi_latch, mtr)) { + latch_mode, cursor, mtr)) { /* Search using the hash index succeeded */ @@ -1330,13 +1327,6 @@ btr_cur_search_to_nth_level_func( /* If the hash search did not succeed, do binary search down the tree */ -#ifdef BTR_CUR_HASH_ADAPT - if (ahi_latch) { - /* Release possible search latch to obey latching order */ - rw_lock_s_unlock(ahi_latch); - } -#endif /* BTR_CUR_HASH_ADAPT */ - /* Store the position of the tree latch we push to mtr so that we know how to release it when we have latched leaf node(s) */ @@ -2397,12 +2387,6 @@ func_exit: cursor->rtr_info->mbr_adj = true; } -#ifdef BTR_CUR_HASH_ADAPT - if (ahi_latch) { - rw_lock_s_lock(ahi_latch); - } -#endif /* BTR_CUR_HASH_ADAPT */ - DBUG_RETURN(err); } @@ -6232,8 +6216,7 @@ btr_estimate_n_rows_in_range_low( btr_cur_search_to_nth_level(index, 0, tuple1, mode1, BTR_SEARCH_LEAF | BTR_ESTIMATE, - &cursor, 0, - __FILE__, __LINE__, &mtr); + &cursor, __FILE__, __LINE__, &mtr); ut_ad(!page_rec_is_infimum(btr_cur_get_rec(&cursor))); @@ -6286,8 +6269,7 @@ btr_estimate_n_rows_in_range_low( btr_cur_search_to_nth_level(index, 0, tuple2, mode2, BTR_SEARCH_LEAF | BTR_ESTIMATE, - &cursor, 0, - __FILE__, __LINE__, &mtr); + &cursor, __FILE__, __LINE__, &mtr); const rec_t* rec = btr_cur_get_rec(&cursor); diff --git a/storage/innobase/btr/btr0pcur.cc b/storage/innobase/btr/btr0pcur.cc index 53963caa023..ac6cd298097 100644 --- a/storage/innobase/btr/btr0pcur.cc +++ b/storage/innobase/btr/btr0pcur.cc @@ -424,11 +424,7 @@ btr_pcur_t::restore_position(ulint restore_latch_mode, const char *file, } btr_pcur_open_with_no_init_func(index, tuple, mode, restore_latch_mode, - this, -#ifdef BTR_CUR_HASH_ADAPT - NULL, -#endif /* BTR_CUR_HASH_ADAPT */ - file, line, mtr); + this, file, line, mtr); /* Restore the old search mode */ search_mode = old_mode; diff --git a/storage/innobase/btr/btr0sea.cc b/storage/innobase/btr/btr0sea.cc index 4b4bba9a941..ff5a0e1e737 100644 --- a/storage/innobase/btr/btr0sea.cc +++ b/storage/innobase/btr/btr0sea.cc @@ -895,8 +895,6 @@ both have sensible values. we assume the caller uses his search latch to protect the record! @param[out] cursor tree cursor -@param[in] ahi_latch the adaptive hash index latch being held, - or NULL @param[in] mtr mini transaction @return whether the search succeeded */ bool @@ -907,7 +905,6 @@ btr_search_guess_on_hash( ulint mode, ulint latch_mode, btr_cur_t* cursor, - rw_lock_t* ahi_latch, mtr_t* mtr) { ulint fold; @@ -916,8 +913,6 @@ btr_search_guess_on_hash( btr_cur_t cursor2; btr_pcur_t pcur; #endif - ut_ad(!ahi_latch || rw_lock_own_flagged( - ahi_latch, RW_LOCK_FLAG_X | RW_LOCK_FLAG_S)); if (!btr_search_enabled) { return false; @@ -925,7 +920,6 @@ btr_search_guess_on_hash( ut_ad(index && info && tuple && cursor && mtr); ut_ad(!dict_index_is_ibuf(index)); - ut_ad(!ahi_latch || ahi_latch == btr_get_search_latch(index)); ut_ad((latch_mode == BTR_SEARCH_LEAF) || (latch_mode == BTR_MODIFY_LEAF)); @@ -956,28 +950,21 @@ btr_search_guess_on_hash( cursor->fold = fold; cursor->flag = BTR_CUR_HASH; - rw_lock_t* use_latch = ahi_latch ? NULL : btr_get_search_latch(index); + rw_lock_t* ahi_latch = btr_get_search_latch(index); const rec_t* rec; - if (use_latch) { - rw_lock_s_lock(use_latch); + rw_lock_s_lock(ahi_latch); - if (!btr_search_enabled) { - goto fail; - } - } else { - ut_ad(btr_search_enabled); - ut_ad(rw_lock_own(ahi_latch, RW_LOCK_S)); + if (!btr_search_enabled) { + goto fail; } rec = static_cast( ha_search_and_get_data(btr_get_search_table(index), fold)); if (!rec) { - if (use_latch) { fail: - rw_lock_s_unlock(use_latch); - } + rw_lock_s_unlock(ahi_latch); btr_search_failure(info, cursor); return false; @@ -985,25 +972,19 @@ fail: buf_block_t* block = buf_block_from_ahi(rec); - if (use_latch) { - if (!buf_page_get_known_nowait( - latch_mode, block, BUF_MAKE_YOUNG, - __FILE__, __LINE__, mtr)) { - goto fail; - } + if (!buf_page_get_known_nowait(latch_mode, block, BUF_MAKE_YOUNG, + __FILE__, __LINE__, mtr)) { + goto fail; + } - const bool fail = index != block->index - && index_id == block->index->id; - ut_a(!fail || block->index->freed()); - rw_lock_s_unlock(use_latch); + const bool fail = index != block->index + && index_id == block->index->id; + ut_a(!fail || block->index->freed()); + ut_ad(fail || !block->page.file_page_was_freed); + rw_lock_s_unlock(ahi_latch); - buf_block_dbg_add_level(block, SYNC_TREE_NODE_FROM_HASH); - if (UNIV_UNLIKELY(fail)) { - goto fail_and_release_page; - } - } else if (UNIV_UNLIKELY(index != block->index - && index_id == block->index->id)) { - ut_a(block->index->freed()); + buf_block_dbg_add_level(block, SYNC_TREE_NODE_FROM_HASH); + if (UNIV_UNLIKELY(fail)) { goto fail_and_release_page; } @@ -1012,9 +993,7 @@ fail: ut_ad(buf_block_get_state(block) == BUF_BLOCK_REMOVE_HASH); fail_and_release_page: - if (!ahi_latch) { - btr_leaf_page_release(block, latch_mode, mtr); - } + btr_leaf_page_release(block, latch_mode, mtr); btr_search_failure(info, cursor); return false; @@ -1032,7 +1011,7 @@ fail_and_release_page: record to determine if our guess for the cursor position is right. */ if (index_id != btr_page_get_index_id(block->frame) - || !btr_search_check_guess(cursor, !!ahi_latch, tuple, mode)) { + || !btr_search_check_guess(cursor, 0, tuple, mode)) { goto fail_and_release_page; } @@ -1081,7 +1060,7 @@ fail_and_release_page: #ifdef UNIV_SEARCH_PERF_STAT btr_search_n_succ++; #endif - if (!ahi_latch && buf_page_peek_if_too_old(&block->page)) { + if (buf_page_peek_if_too_old(&block->page)) { buf_page_make_young(&block->page); } diff --git a/storage/innobase/buf/buf0buf.cc b/storage/innobase/buf/buf0buf.cc index c50c645342a..01111157920 100644 --- a/storage/innobase/buf/buf0buf.cc +++ b/storage/innobase/buf/buf0buf.cc @@ -4815,6 +4815,10 @@ buf_page_get_known_nowait( ut_a(buf_block_get_state(block) == BUF_BLOCK_FILE_PAGE); + /* The check for the page was not freed would already have been + performed when the block descriptor was acquired by the thread for the + first time.*/ + buf_block_buf_fix_inc(block, file, line); buf_page_set_accessed(&block->page); @@ -4861,24 +4865,6 @@ buf_page_get_known_nowait( ut_a(buf_block_get_state(block) == BUF_BLOCK_FILE_PAGE); #endif /* UNIV_DEBUG || UNIV_BUF_DEBUG */ -#ifdef UNIV_DEBUG - if (mode != BUF_KEEP_OLD) { - /* If mode == BUF_KEEP_OLD, we are executing an I/O - completion routine. Avoid a bogus assertion failure - when ibuf_merge_or_delete_for_page() is processing a - page that was just freed due to DROP INDEX, or - deleting a record from SYS_INDEXES. This check will be - skipped in recv_recover_page() as well. */ - -# ifdef BTR_CUR_HASH_ADAPT - ut_ad(!block->page.file_page_was_freed - || btr_search_check_marked_free_index(block)); -# else /* BTR_CUR_HASH_ADAPT */ - ut_ad(!block->page.file_page_was_freed); -# endif /* BTR_CUR_HASH_ADAPT */ - } -#endif /* UNIV_DEBUG */ - buf_pool->stat.n_page_gets++; return(TRUE); diff --git a/storage/innobase/dict/dict0dict.cc b/storage/innobase/dict/dict0dict.cc index eb0f10d55f4..d843115082e 100644 --- a/storage/innobase/dict/dict0dict.cc +++ b/storage/innobase/dict/dict0dict.cc @@ -5435,7 +5435,7 @@ dict_set_corrupted( btr_cur_search_to_nth_level(sys_index, 0, tuple, PAGE_CUR_LE, BTR_MODIFY_LEAF, - &cursor, 0, __FILE__, __LINE__, &mtr); + &cursor, __FILE__, __LINE__, &mtr); if (cursor.low_match == dtuple_get_n_fields(tuple)) { /* UPDATE SYS_INDEXES SET TYPE=index->type @@ -5538,7 +5538,7 @@ dict_index_set_merge_threshold( btr_cur_search_to_nth_level(sys_index, 0, tuple, PAGE_CUR_GE, BTR_MODIFY_LEAF, - &cursor, 0, __FILE__, __LINE__, &mtr); + &cursor, __FILE__, __LINE__, &mtr); if (cursor.up_match == dtuple_get_n_fields(tuple) && rec_get_n_fields_old(btr_cur_get_rec(&cursor)) diff --git a/storage/innobase/fts/fts0fts.cc b/storage/innobase/fts/fts0fts.cc index b16bb6611b0..dc8d529d79c 100644 --- a/storage/innobase/fts/fts0fts.cc +++ b/storage/innobase/fts/fts0fts.cc @@ -3437,7 +3437,7 @@ fts_add_doc_by_id( btr_pcur_open_with_no_init( fts_id_index, tuple, PAGE_CUR_LE, BTR_SEARCH_LEAF, - &pcur, 0, &mtr); + &pcur, &mtr); /* If we have a match, add the data to doc structure */ if (btr_pcur_get_low_match(&pcur) == 1) { @@ -3475,7 +3475,7 @@ fts_add_doc_by_id( btr_pcur_open_with_no_init( clust_index, clust_ref, PAGE_CUR_LE, - BTR_SEARCH_LEAF, &clust_pcur, 0, &mtr); + BTR_SEARCH_LEAF, &clust_pcur, &mtr); doc_pcur = &clust_pcur; clust_rec = btr_pcur_get_rec(&clust_pcur); diff --git a/storage/innobase/gis/gis0sea.cc b/storage/innobase/gis/gis0sea.cc index e5ba43faa0b..5e52b7a70c4 100644 --- a/storage/innobase/gis/gis0sea.cc +++ b/storage/innobase/gis/gis0sea.cc @@ -588,7 +588,7 @@ rtr_pcur_open_low( } btr_cur_search_to_nth_level(index, level, tuple, mode, latch_mode, - btr_cursor, 0, file, line, mtr); + btr_cursor, file, line, mtr); cursor->pos_state = BTR_PCUR_IS_POSITIONED; cursor->trx_if_known = NULL; @@ -756,8 +756,7 @@ static void rtr_get_father_node( /* root split, and search the new root */ btr_cur_search_to_nth_level( index, level, tuple, PAGE_CUR_RTREE_LOCATE, - BTR_CONT_MODIFY_TREE, btr_cur, 0, - __FILE__, __LINE__, mtr); + BTR_CONT_MODIFY_TREE, btr_cur, __FILE__, __LINE__, mtr); } else { /* btr_validate */ @@ -766,8 +765,7 @@ static void rtr_get_father_node( btr_cur_search_to_nth_level( index, level, tuple, PAGE_CUR_RTREE_LOCATE, - BTR_CONT_MODIFY_TREE, btr_cur, 0, - __FILE__, __LINE__, mtr); + BTR_CONT_MODIFY_TREE, btr_cur, __FILE__, __LINE__, mtr); rec = btr_cur_get_rec(btr_cur); n_fields = dtuple_get_n_fields_cmp(tuple); diff --git a/storage/innobase/include/btr0cur.h b/storage/innobase/include/btr0cur.h index db903df925c..5755c7c5bcf 100644 --- a/storage/innobase/include/btr0cur.h +++ b/storage/innobase/include/btr0cur.h @@ -170,56 +170,41 @@ btr_cur_optimistic_latch_leaves( unsigned line, mtr_t* mtr); -/********************************************************************//** -Searches an index tree and positions a tree cursor on a given level. +/** Searches an index tree and positions a tree cursor on a given level. NOTE: n_fields_cmp in tuple must be set so that it cannot be compared to node pointer page number fields on the upper levels of the tree! Note that if mode is PAGE_CUR_LE, which is used in inserts, then cursor->up_match and cursor->low_match both will have sensible values. -If mode is PAGE_CUR_GE, then up_match will a have a sensible value. */ -dberr_t -btr_cur_search_to_nth_level_func( - dict_index_t* index, /*!< in: index */ - ulint level, /*!< in: the tree level of search */ - const dtuple_t* tuple, /*!< in: data tuple; NOTE: n_fields_cmp in - tuple must be set so that it cannot get - compared to the node ptr page number field! */ - page_cur_mode_t mode, /*!< in: PAGE_CUR_L, ...; - NOTE that if the search is made using a unique - prefix of a record, mode should be PAGE_CUR_LE, - not PAGE_CUR_GE, as the latter may end up on - the previous page of the record! Inserts - should always be made using PAGE_CUR_LE to - search the position! */ - ulint latch_mode, /*!< in: BTR_SEARCH_LEAF, ..., ORed with - at most one of BTR_INSERT, BTR_DELETE_MARK, - BTR_DELETE, or BTR_ESTIMATE; - cursor->left_block is used to store a pointer - to the left neighbor page, in the cases - BTR_SEARCH_PREV and BTR_MODIFY_PREV; - NOTE that if ahi_latch, we might not have a - cursor page latch, we assume that ahi_latch - protects the record! */ - btr_cur_t* cursor, /*!< in/out: tree cursor; the cursor page is - s- or x-latched, but see also above! */ -#ifdef BTR_CUR_HASH_ADAPT - rw_lock_t* ahi_latch, - /*!< in: currently held btr_search_latch - (in RW_S_LATCH mode), or NULL */ -#endif /* BTR_CUR_HASH_ADAPT */ - const char* file, /*!< in: file name */ - unsigned line, /*!< in: line where called */ - mtr_t* mtr, /*!< in/out: mini-transaction */ - ib_uint64_t autoinc = 0); - /*!< in: PAGE_ROOT_AUTO_INC to be written - (0 if none) */ -#ifdef BTR_CUR_HASH_ADAPT -# define btr_cur_search_to_nth_level(i,l,t,m,lm,c,a,fi,li,mtr) \ - btr_cur_search_to_nth_level_func(i,l,t,m,lm,c,a,fi,li,mtr) -#else /* BTR_CUR_HASH_ADAPT */ -# define btr_cur_search_to_nth_level(i,l,t,m,lm,c,a,fi,li,mtr) \ - btr_cur_search_to_nth_level_func(i,l,t,m,lm,c,fi,li,mtr) -#endif /* BTR_CUR_HASH_ADAPT */ +If mode is PAGE_CUR_GE, then up_match will a have a sensible value. +@param index index +@param level the tree level of search +@param tuple data tuple; NOTE: n_fields_cmp in tuple must be set so that + it cannot get compared to the node ptr page number field! +@param mode PAGE_CUR_L, NOTE that if the search is made using a unique + prefix of a record, mode should be PAGE_CUR_LE, not + PAGE_CUR_GE, as the latter may end up on the previous page of + the record! Inserts should always be made using PAGE_CUR_LE + to search the position! +@param latch_mode BTR_SEARCH_LEAF, ..., ORed with at most one of BTR_INSERT, + BTR_DELETE_MARK, BTR_DELETE, or BTR_ESTIMATE; + cursor->left_block is used to store a pointer to the left + neighbor page, in the cases BTR_SEARCH_PREV and + BTR_MODIFY_PREV; NOTE that if ahi_latch, we might not have a + cursor page latch, we assume that ahi_latch protects the + record! +@param cursor tree cursor; the cursor page is s- or x-latched, but see also + above! +@param file file name +@param line line where called +@param mtr mini-transaction +@param autoinc PAGE_ROOT_AUTO_INC to be written (0 if none) +@return DB_SUCCESS on success or error code otherwise */ +dberr_t btr_cur_search_to_nth_level(dict_index_t *index, ulint level, + const dtuple_t *tuple, + page_cur_mode_t mode, ulint latch_mode, + btr_cur_t *cursor, const char *file, + unsigned line, mtr_t *mtr, + ib_uint64_t autoinc= 0); /*****************************************************************//** Opens a cursor at either end of an index. diff --git a/storage/innobase/include/btr0pcur.h b/storage/innobase/include/btr0pcur.h index bbb9831ae93..ca17dd95aa7 100644 --- a/storage/innobase/include/btr0pcur.h +++ b/storage/innobase/include/btr0pcur.h @@ -116,41 +116,30 @@ btr_pcur_open_low( mtr_t* mtr); /*!< in: mtr */ #define btr_pcur_open(i,t,md,l,c,m) \ btr_pcur_open_low(i,0,t,md,l,c,__FILE__,__LINE__,0,m) -/**************************************************************//** -Opens an persistent cursor to an index tree without initializing the -cursor. */ +/** Opens an persistent cursor to an index tree without initializing the +cursor. +@param index index +@param tuple tuple on which search done +@param mode PAGE_CUR_L, ...; NOTE that if the search is made using a + unique prefix of a record, mode should be PAGE_CUR_LE, not + PAGE_CUR_GE, as the latter may end up on the previous page of + the record! +@param latch_mode BTR_SEARCH_LEAF, ...; NOTE that if ahi_latch then we might + not acquire a cursor page latch, but assume that the + ahi_latch protects the record! +@param cursor memory buffer for persistent cursor +@param file file name +@param line line where called +@param mtr mtr +@return DB_SUCCESS on success or error code otherwise. */ UNIV_INLINE -dberr_t -btr_pcur_open_with_no_init_func( -/*============================*/ - dict_index_t* index, /*!< in: index */ - const dtuple_t* tuple, /*!< in: tuple on which search done */ - page_cur_mode_t mode, /*!< in: PAGE_CUR_L, ...; - NOTE that if the search is made using a unique - prefix of a record, mode should be - PAGE_CUR_LE, not PAGE_CUR_GE, as the latter - may end up on the previous page of the - record! */ - ulint latch_mode,/*!< in: BTR_SEARCH_LEAF, ...; - NOTE that if ahi_latch then we might not - acquire a cursor page latch, but assume - that the ahi_latch protects the record! */ - btr_pcur_t* cursor, /*!< in: memory buffer for persistent cursor */ -#ifdef BTR_CUR_HASH_ADAPT - rw_lock_t* ahi_latch, - /*!< in: adaptive hash index latch held - by the caller, or NULL if none */ -#endif /* BTR_CUR_HASH_ADAPT */ - const char* file, /*!< in: file name */ - unsigned line, /*!< in: line where called */ - mtr_t* mtr); /*!< in: mtr */ -#ifdef BTR_CUR_HASH_ADAPT -# define btr_pcur_open_with_no_init(ix,t,md,l,cur,ahi,m) \ - btr_pcur_open_with_no_init_func(ix,t,md,l,cur,ahi,__FILE__,__LINE__,m) -#else /* BTR_CUR_HASH_ADAPT */ -# define btr_pcur_open_with_no_init(ix,t,md,l,cur,ahi,m) \ +dberr_t btr_pcur_open_with_no_init_func(dict_index_t *index, + const dtuple_t *tuple, + page_cur_mode_t mode, ulint latch_mode, + btr_pcur_t *cursor, const char *file, + unsigned line, mtr_t *mtr); +# define btr_pcur_open_with_no_init(ix,t,md,l,cur,m) \ btr_pcur_open_with_no_init_func(ix,t,md,l,cur,__FILE__,__LINE__,m) -#endif /* BTR_CUR_HASH_ADAPT */ /*****************************************************************//** Opens a persistent cursor at either end of an index. */ diff --git a/storage/innobase/include/btr0pcur.inl b/storage/innobase/include/btr0pcur.inl index d93da475a1f..05f61b903ff 100644 --- a/storage/innobase/include/btr0pcur.inl +++ b/storage/innobase/include/btr0pcur.inl @@ -438,11 +438,8 @@ btr_pcur_open_low( ut_ad(!dict_index_is_spatial(index)); - err = btr_cur_search_to_nth_level_func( + err = btr_cur_search_to_nth_level( index, level, tuple, mode, latch_mode, btr_cursor, -#ifdef BTR_CUR_HASH_ADAPT - NULL, -#endif /* BTR_CUR_HASH_ADAPT */ file, line, mtr, autoinc); if (UNIV_UNLIKELY(err != DB_SUCCESS)) { @@ -462,34 +459,28 @@ btr_pcur_open_low( return(err); } -/**************************************************************//** -Opens an persistent cursor to an index tree without initializing the -cursor. */ +/** Opens an persistent cursor to an index tree without initializing the +cursor. +@param index index +@param tuple tuple on which search done +@param mode PAGE_CUR_L, ...; NOTE that if the search is made using a + unique prefix of a record, mode should be PAGE_CUR_LE, not + PAGE_CUR_GE, as the latter may end up on the previous page of + the record! +@param latch_mode BTR_SEARCH_LEAF, ...; NOTE that if ahi_latch then we might + not acquire a cursor page latch, but assume that the + ahi_latch protects the record! +@param cursor memory buffer for persistent cursor +@param file file name +@param line line where called +@param mtr mtr +@return DB_SUCCESS on success or error code otherwise. */ UNIV_INLINE -dberr_t -btr_pcur_open_with_no_init_func( -/*============================*/ - dict_index_t* index, /*!< in: index */ - const dtuple_t* tuple, /*!< in: tuple on which search done */ - page_cur_mode_t mode, /*!< in: PAGE_CUR_L, ...; - NOTE that if the search is made using a unique - prefix of a record, mode should be - PAGE_CUR_LE, not PAGE_CUR_GE, as the latter - may end up on the previous page of the - record! */ - ulint latch_mode,/*!< in: BTR_SEARCH_LEAF, ...; - NOTE that if ahi_latch then we might not - acquire a cursor page latch, but assume - that the ahi_latch protects the record! */ - btr_pcur_t* cursor, /*!< in: memory buffer for persistent cursor */ -#ifdef BTR_CUR_HASH_ADAPT - rw_lock_t* ahi_latch, - /*!< in: adaptive hash index latch held - by the caller, or NULL if none */ -#endif /* BTR_CUR_HASH_ADAPT */ - const char* file, /*!< in: file name */ - unsigned line, /*!< in: line where called */ - mtr_t* mtr) /*!< in: mtr */ +dberr_t btr_pcur_open_with_no_init_func(dict_index_t *index, + const dtuple_t *tuple, + page_cur_mode_t mode, ulint latch_mode, + btr_pcur_t *cursor, const char *file, + unsigned line, mtr_t *mtr) { btr_cur_t* btr_cursor; dberr_t err = DB_SUCCESS; @@ -501,11 +492,8 @@ btr_pcur_open_with_no_init_func( btr_cursor = btr_pcur_get_btr_cur(cursor); - err = btr_cur_search_to_nth_level_func( + err = btr_cur_search_to_nth_level( index, 0, tuple, mode, latch_mode, btr_cursor, -#ifdef BTR_CUR_HASH_ADAPT - ahi_latch, -#endif /* BTR_CUR_HASH_ADAPT */ file, line, mtr); cursor->pos_state = BTR_PCUR_IS_POSITIONED; diff --git a/storage/innobase/include/btr0sea.h b/storage/innobase/include/btr0sea.h index 8277be8ac14..f217f8213f8 100644 --- a/storage/innobase/include/btr0sea.h +++ b/storage/innobase/include/btr0sea.h @@ -80,7 +80,6 @@ btr_search_guess_on_hash( ulint mode, ulint latch_mode, btr_cur_t* cursor, - rw_lock_t* ahi_latch, mtr_t* mtr); /** Move or delete hash entries for moved records, usually in a page split. diff --git a/storage/innobase/row/row0ins.cc b/storage/innobase/row/row0ins.cc index 82ecc02f2ec..f03381a2fcf 100644 --- a/storage/innobase/row/row0ins.cc +++ b/storage/innobase/row/row0ins.cc @@ -1137,7 +1137,7 @@ row_ins_foreign_check_on_constraint( tmp_heap); btr_pcur_open_with_no_init(clust_index, ref, PAGE_CUR_LE, BTR_SEARCH_LEAF, - cascade->pcur, 0, mtr); + cascade->pcur, mtr); clust_rec = btr_pcur_get_rec(cascade->pcur); clust_block = btr_pcur_get_block(cascade->pcur); @@ -2958,7 +2958,7 @@ row_ins_sec_index_entry_low( err = btr_cur_search_to_nth_level( index, 0, entry, PAGE_CUR_RTREE_INSERT, search_mode, - &cursor, 0, __FILE__, __LINE__, &mtr); + &cursor, __FILE__, __LINE__, &mtr); if (mode == BTR_MODIFY_LEAF && rtr_info.mbr_adj) { mtr_commit(&mtr); @@ -2977,7 +2977,7 @@ row_ins_sec_index_entry_low( err = btr_cur_search_to_nth_level( index, 0, entry, PAGE_CUR_RTREE_INSERT, search_mode, - &cursor, 0, __FILE__, __LINE__, &mtr); + &cursor, __FILE__, __LINE__, &mtr); mode = BTR_MODIFY_TREE; } @@ -2989,7 +2989,7 @@ row_ins_sec_index_entry_low( err = btr_cur_search_to_nth_level( index, 0, entry, PAGE_CUR_LE, search_mode, - &cursor, 0, __FILE__, __LINE__, &mtr); + &cursor, __FILE__, __LINE__, &mtr); } if (err != DB_SUCCESS) { @@ -3083,7 +3083,7 @@ row_ins_sec_index_entry_low( index, 0, entry, PAGE_CUR_LE, (search_mode & ~(BTR_INSERT | BTR_IGNORE_SEC_UNIQUE)), - &cursor, 0, __FILE__, __LINE__, &mtr); + &cursor, __FILE__, __LINE__, &mtr); } if (row_ins_must_modify_rec(&cursor)) { diff --git a/storage/innobase/row/row0log.cc b/storage/innobase/row/row0log.cc index 8bf70f61d07..c91f5b96617 100644 --- a/storage/innobase/row/row0log.cc +++ b/storage/innobase/row/row0log.cc @@ -3354,7 +3354,7 @@ row_log_apply_op_low( has_index_lock ? BTR_MODIFY_TREE : BTR_MODIFY_LEAF, - &cursor, 0, __FILE__, __LINE__, + &cursor, __FILE__, __LINE__, &mtr); ut_ad(dict_index_get_n_unique(index) > 0); @@ -3403,7 +3403,7 @@ row_log_apply_op_low( index->set_modified(mtr); btr_cur_search_to_nth_level( index, 0, entry, PAGE_CUR_LE, - BTR_MODIFY_TREE, &cursor, 0, + BTR_MODIFY_TREE, &cursor, __FILE__, __LINE__, &mtr); /* No other thread than the current one @@ -3506,7 +3506,7 @@ insert_the_rec: index->set_modified(mtr); btr_cur_search_to_nth_level( index, 0, entry, PAGE_CUR_LE, - BTR_MODIFY_TREE, &cursor, 0, + BTR_MODIFY_TREE, &cursor, __FILE__, __LINE__, &mtr); } diff --git a/storage/innobase/row/row0merge.cc b/storage/innobase/row/row0merge.cc index 3fee9d0e6da..3d729b54f7c 100644 --- a/storage/innobase/row/row0merge.cc +++ b/storage/innobase/row/row0merge.cc @@ -163,7 +163,7 @@ public: btr_cur_search_to_nth_level(m_index, 0, dtuple, PAGE_CUR_RTREE_INSERT, BTR_MODIFY_LEAF, &ins_cur, - 0, __FILE__, __LINE__, + __FILE__, __LINE__, &mtr); /* It need to update MBR in parent entry, @@ -179,7 +179,7 @@ public: btr_cur_search_to_nth_level( m_index, 0, dtuple, PAGE_CUR_RTREE_INSERT, - BTR_MODIFY_TREE, &ins_cur, 0, + BTR_MODIFY_TREE, &ins_cur, __FILE__, __LINE__, &mtr); } @@ -202,8 +202,7 @@ public: m_index, 0, dtuple, PAGE_CUR_RTREE_INSERT, BTR_MODIFY_TREE, - &ins_cur, 0, - __FILE__, __LINE__, &mtr); + &ins_cur, __FILE__, __LINE__, &mtr); error = btr_cur_pessimistic_insert( flag, &ins_cur, &ins_offsets, diff --git a/storage/innobase/row/row0sel.cc b/storage/innobase/row/row0sel.cc index c718a53db61..d9b517309c6 100644 --- a/storage/innobase/row/row0sel.cc +++ b/storage/innobase/row/row0sel.cc @@ -985,8 +985,7 @@ row_sel_get_clust_rec( index = dict_table_get_first_index(plan->table); btr_pcur_open_with_no_init(index, plan->clust_ref, PAGE_CUR_LE, - BTR_SEARCH_LEAF, &plan->clust_pcur, - 0, mtr); + BTR_SEARCH_LEAF, &plan->clust_pcur, mtr); clust_rec = btr_pcur_get_rec(&(plan->clust_pcur)); @@ -1394,8 +1393,7 @@ row_sel_open_pcur( /* Open pcur to the index */ btr_pcur_open_with_no_init(index, plan->tuple, plan->mode, - BTR_SEARCH_LEAF, &plan->pcur, - NULL, mtr); + BTR_SEARCH_LEAF, &plan->pcur, mtr); } else { /* Open the cursor to the start or the end of the index (FALSE: no init) */ @@ -3369,7 +3367,7 @@ Row_sel_get_clust_rec_for_mysql::operator()( btr_pcur_open_with_no_init(clust_index, prebuilt->clust_ref, PAGE_CUR_LE, BTR_SEARCH_LEAF, - prebuilt->clust_pcur, 0, mtr); + prebuilt->clust_pcur, mtr); clust_rec = btr_pcur_get_rec(prebuilt->clust_pcur); @@ -3952,15 +3950,12 @@ row_sel_try_search_shortcut_for_mysql( ut_ad(dict_index_is_clust(index)); ut_ad(!prebuilt->templ_contains_blob); - rw_lock_t* ahi_latch = btr_get_search_latch(index); - rw_lock_s_lock(ahi_latch); btr_pcur_open_with_no_init(index, search_tuple, PAGE_CUR_GE, - BTR_SEARCH_LEAF, pcur, ahi_latch, mtr); + BTR_SEARCH_LEAF, pcur, mtr); rec = btr_pcur_get_rec(pcur); if (!page_rec_is_user_rec(rec) || rec_is_metadata(rec, index)) { retry: - rw_lock_s_unlock(ahi_latch); return(SEL_RETRY); } @@ -3970,7 +3965,6 @@ retry: if (btr_pcur_get_up_match(pcur) < dtuple_get_n_fields(search_tuple)) { exhausted: - rw_lock_s_unlock(ahi_latch); return(SEL_EXHAUSTED); } @@ -3994,7 +3988,6 @@ exhausted: *out_rec = rec; - rw_lock_s_unlock(ahi_latch); return(SEL_FOUND); } #endif /* BTR_CUR_HASH_ADAPT */ @@ -4728,8 +4721,7 @@ wait_table_again: } err = btr_pcur_open_with_no_init(index, search_tuple, mode, - BTR_SEARCH_LEAF, - pcur, 0, &mtr); + BTR_SEARCH_LEAF, pcur, &mtr); if (err != DB_SUCCESS) { rec = NULL; -- cgit v1.2.1 From f600690c6be112e2f2b36ffb80c103bbd50814f5 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Marko=20M=C3=A4kel=C3=A4?= Date: Wed, 5 Oct 2022 20:37:54 +0300 Subject: MDEV-29710: Skip some more tests on Valgrind --- mysql-test/main/rowid_filter_innodb_debug.test | 1 + mysql-test/suite/federated/federatedx_create_handlers.test | 1 + mysql-test/suite/innodb/t/alter_copy.test | 1 + mysql-test/suite/innodb/t/autoinc_persist.test | 1 + mysql-test/suite/innodb/t/innodb-stats-initialize-failure.test | 1 + mysql-test/suite/innodb/t/innodb-stats-sample.test | 1 + mysql-test/suite/innodb/t/innodb-trim.test | 1 + mysql-test/suite/innodb/t/innodb_bug30423.test | 1 + mysql-test/suite/innodb/t/log_corruption.test | 1 + mysql-test/suite/innodb/t/log_file.test | 1 + mysql-test/suite/innodb/t/log_file_name.test | 1 + mysql-test/suite/innodb/t/read_only_recover_committed.test | 1 + mysql-test/suite/innodb/t/recovery_shutdown.test | 1 + mysql-test/suite/innodb/t/undo_truncate.test | 1 + mysql-test/suite/innodb_fts/t/innodb_fts_plugin.test | 1 + mysql-test/suite/rpl/t/rpl_semi_sync_shutdown_await_ack.test | 2 ++ mysql-test/suite/stress/t/ddl_innodb.test | 1 + 17 files changed, 18 insertions(+) diff --git a/mysql-test/main/rowid_filter_innodb_debug.test b/mysql-test/main/rowid_filter_innodb_debug.test index eb43edd9e9e..31fbd937304 100644 --- a/mysql-test/main/rowid_filter_innodb_debug.test +++ b/mysql-test/main/rowid_filter_innodb_debug.test @@ -1,4 +1,5 @@ --source include/have_innodb.inc +--source include/no_valgrind_without_big.inc set default_storage_engine=innodb; --source include/rowid_filter_debug_kill.inc diff --git a/mysql-test/suite/federated/federatedx_create_handlers.test b/mysql-test/suite/federated/federatedx_create_handlers.test index 4b5789e1d96..8863a057b47 100644 --- a/mysql-test/suite/federated/federatedx_create_handlers.test +++ b/mysql-test/suite/federated/federatedx_create_handlers.test @@ -1,5 +1,6 @@ --source have_federatedx.inc --source include/federated.inc +--source include/no_valgrind_without_big.inc connection default; diff --git a/mysql-test/suite/innodb/t/alter_copy.test b/mysql-test/suite/innodb/t/alter_copy.test index b7ab05a061a..ac1288adb0c 100644 --- a/mysql-test/suite/innodb/t/alter_copy.test +++ b/mysql-test/suite/innodb/t/alter_copy.test @@ -2,6 +2,7 @@ --source include/have_debug.inc --source include/have_debug_sync.inc --source include/not_embedded.inc +--source include/no_valgrind_without_big.inc --echo # --echo # MDEV-11415 AVOID INTERMEDIATE COMMIT WHILE DOING diff --git a/mysql-test/suite/innodb/t/autoinc_persist.test b/mysql-test/suite/innodb/t/autoinc_persist.test index fd85b45fbfa..f2175bd7f63 100644 --- a/mysql-test/suite/innodb/t/autoinc_persist.test +++ b/mysql-test/suite/innodb/t/autoinc_persist.test @@ -1,6 +1,7 @@ --source include/have_innodb.inc # Restarting is not supported when testing the embedded server. --source include/not_embedded.inc +--source include/no_valgrind_without_big.inc --echo # --echo # MDEV-6076 Persistent AUTO_INCREMENT for InnoDB diff --git a/mysql-test/suite/innodb/t/innodb-stats-initialize-failure.test b/mysql-test/suite/innodb/t/innodb-stats-initialize-failure.test index d5d04190b8a..ba37e82057f 100644 --- a/mysql-test/suite/innodb/t/innodb-stats-initialize-failure.test +++ b/mysql-test/suite/innodb/t/innodb-stats-initialize-failure.test @@ -1,5 +1,6 @@ # MDEV-6424: Mariadb server crashes with assertion failure in file ha_innodb.cc --source include/have_innodb.inc +--source include/no_valgrind_without_big.inc # DEBUG_SYNC must be compiled in. --source include/have_debug_sync.inc diff --git a/mysql-test/suite/innodb/t/innodb-stats-sample.test b/mysql-test/suite/innodb/t/innodb-stats-sample.test index 35d35bfa382..de1b0d017e9 100644 --- a/mysql-test/suite/innodb/t/innodb-stats-sample.test +++ b/mysql-test/suite/innodb/t/innodb-stats-sample.test @@ -1,4 +1,5 @@ --source include/have_innodb.inc +--source include/no_valgrind_without_big.inc # # Test that mysqld does not crash when running ANALYZE TABLE with # different values of the parameter innodb_stats_sample_pages. diff --git a/mysql-test/suite/innodb/t/innodb-trim.test b/mysql-test/suite/innodb/t/innodb-trim.test index 0f38ea5ba84..ea2ac402977 100644 --- a/mysql-test/suite/innodb/t/innodb-trim.test +++ b/mysql-test/suite/innodb/t/innodb-trim.test @@ -1,5 +1,6 @@ --source include/have_innodb.inc --source include/have_innodb_punchhole.inc +--source include/no_valgrind_without_big.inc --disable_query_log --disable_warnings diff --git a/mysql-test/suite/innodb/t/innodb_bug30423.test b/mysql-test/suite/innodb/t/innodb_bug30423.test index de53a935156..9d9975c04ca 100644 --- a/mysql-test/suite/innodb/t/innodb_bug30423.test +++ b/mysql-test/suite/innodb/t/innodb_bug30423.test @@ -1,4 +1,5 @@ --source include/have_innodb.inc +--source include/no_valgrind_without_big.inc # Test for Bug #30423, InnoDBs treatment of NULL in index stats causes # bad "rows examined" estimates. # Implemented InnoDB system variable "innodb_stats_method" with diff --git a/mysql-test/suite/innodb/t/log_corruption.test b/mysql-test/suite/innodb/t/log_corruption.test index 3d68724f7a9..38048505aea 100644 --- a/mysql-test/suite/innodb/t/log_corruption.test +++ b/mysql-test/suite/innodb/t/log_corruption.test @@ -1,5 +1,6 @@ --source include/have_innodb.inc --source include/have_innodb_16k.inc +--source include/no_valgrind_without_big.inc --disable_query_log call mtr.add_suppression("InnoDB: Upgrade after a crash is not supported"); diff --git a/mysql-test/suite/innodb/t/log_file.test b/mysql-test/suite/innodb/t/log_file.test index 7aca2336de6..1e96e9c26e4 100644 --- a/mysql-test/suite/innodb/t/log_file.test +++ b/mysql-test/suite/innodb/t/log_file.test @@ -3,6 +3,7 @@ --echo # Bug#16418661 - CHANGING NAME IN FOR INNODB_DATA_FILE_PATH SHOULD NOT SUCCEED WITH LOG FILES --source include/have_innodb.inc +--source include/no_valgrind_without_big.inc --disable_query_log call mtr.add_suppression("InnoDB: Could not create undo tablespace.*undo002"); diff --git a/mysql-test/suite/innodb/t/log_file_name.test b/mysql-test/suite/innodb/t/log_file_name.test index 80b4e3d3921..0aad3f88936 100644 --- a/mysql-test/suite/innodb/t/log_file_name.test +++ b/mysql-test/suite/innodb/t/log_file_name.test @@ -2,6 +2,7 @@ # Test the detection of duplicate tablespaces. --source include/have_innodb.inc +--source include/no_valgrind_without_big.inc # Embedded server does not support crashing --source include/not_embedded.inc diff --git a/mysql-test/suite/innodb/t/read_only_recover_committed.test b/mysql-test/suite/innodb/t/read_only_recover_committed.test index 439f57e9fad..5c4eac86c26 100644 --- a/mysql-test/suite/innodb/t/read_only_recover_committed.test +++ b/mysql-test/suite/innodb/t/read_only_recover_committed.test @@ -1,6 +1,7 @@ --source include/have_innodb.inc --source include/have_debug.inc --source include/have_debug_sync.inc +--source include/no_valgrind_without_big.inc # need to restart server --source include/not_embedded.inc diff --git a/mysql-test/suite/innodb/t/recovery_shutdown.test b/mysql-test/suite/innodb/t/recovery_shutdown.test index d72e785f21d..f439ccac51a 100644 --- a/mysql-test/suite/innodb/t/recovery_shutdown.test +++ b/mysql-test/suite/innodb/t/recovery_shutdown.test @@ -1,5 +1,6 @@ --source include/have_innodb.inc --source include/not_embedded.inc +--source include/no_valgrind_without_big.inc # Flush any open myisam tables from previous tests FLUSH TABLES; diff --git a/mysql-test/suite/innodb/t/undo_truncate.test b/mysql-test/suite/innodb/t/undo_truncate.test index 0e73a9b4e21..e2648fa761a 100644 --- a/mysql-test/suite/innodb/t/undo_truncate.test +++ b/mysql-test/suite/innodb/t/undo_truncate.test @@ -3,6 +3,7 @@ --source include/have_undo_tablespaces.inc --source include/not_embedded.inc --source include/have_sequence.inc +--source include/no_valgrind_without_big.inc SET GLOBAL innodb_undo_log_truncate = 0; SET GLOBAL innodb_purge_rseg_truncate_frequency = 1; diff --git a/mysql-test/suite/innodb_fts/t/innodb_fts_plugin.test b/mysql-test/suite/innodb_fts/t/innodb_fts_plugin.test index 7279925386b..3f9d1f8faf1 100644 --- a/mysql-test/suite/innodb_fts/t/innodb_fts_plugin.test +++ b/mysql-test/suite/innodb_fts/t/innodb_fts_plugin.test @@ -1,5 +1,6 @@ --source include/have_innodb.inc --source include/have_simple_parser.inc +--source include/no_valgrind_without_big.inc # Restart is not supported in embedded --source include/not_embedded.inc diff --git a/mysql-test/suite/rpl/t/rpl_semi_sync_shutdown_await_ack.test b/mysql-test/suite/rpl/t/rpl_semi_sync_shutdown_await_ack.test index 5e9cda6466e..2ee7d0aa052 100644 --- a/mysql-test/suite/rpl/t/rpl_semi_sync_shutdown_await_ack.test +++ b/mysql-test/suite/rpl/t/rpl_semi_sync_shutdown_await_ack.test @@ -1,3 +1,5 @@ +--source include/no_valgrind_without_big.inc + # # Purpose: # This test validates that data is consistent between a primary and replica diff --git a/mysql-test/suite/stress/t/ddl_innodb.test b/mysql-test/suite/stress/t/ddl_innodb.test index 083ec43e7d7..d5e23124b4b 100644 --- a/mysql-test/suite/stress/t/ddl_innodb.test +++ b/mysql-test/suite/stress/t/ddl_innodb.test @@ -1,3 +1,4 @@ +--source include/no_valgrind_without_big.inc ######## t/ddl_innodb.test ###### # # Stress the storage engine InnoDB with CREATE/DROP TABLE/INDEX -- cgit v1.2.1 From ba9ade47e3acf1e0f72a52f24832cd6b3619fb5f Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Marko=20M=C3=A4kel=C3=A4?= Date: Thu, 6 Oct 2022 07:38:46 +0300 Subject: MDEV-29710: Skip main.update_use_source on Valgrind This test is not slow, but it reliably produces an EXPLAIN difference (number of rows) on the Valgrind builder. A possible explanation could be that the purge threads are not being scheduled. Valgrind runs all threads in a single thread. --- mysql-test/main/update_use_source.test | 1 + 1 file changed, 1 insertion(+) diff --git a/mysql-test/main/update_use_source.test b/mysql-test/main/update_use_source.test index 7ed5f95d68d..a73bbba7613 100644 --- a/mysql-test/main/update_use_source.test +++ b/mysql-test/main/update_use_source.test @@ -1,5 +1,6 @@ --source include/have_sequence.inc --source include/have_innodb.inc +--source include/no_valgrind_without_big.inc create table t1 (old_c1 integer, old_c2 integer,c1 integer, c2 integer, c3 integer) engine=InnoDb; create view v1 as select * from t1 where c2=2; -- cgit v1.2.1 From 3708bef60683dc7b6020ee76e90738528ccad18a Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Marko=20M=C3=A4kel=C3=A4?= Date: Thu, 6 Oct 2022 07:40:00 +0300 Subject: MDEV-27682: Temporarily disable a failing test --- mysql-test/suite/galera/disabled.def | 1 + 1 file changed, 1 insertion(+) diff --git a/mysql-test/suite/galera/disabled.def b/mysql-test/suite/galera/disabled.def index 6727aa3d945..ade0e8257e5 100644 --- a/mysql-test/suite/galera/disabled.def +++ b/mysql-test/suite/galera/disabled.def @@ -24,6 +24,7 @@ galera_shutdown_nonprim : MDEV-21493 galera.galera_shutdown_nonprim galera_var_ignore_apply_errors : MDEV-26770 galera_var_ignore_apply_errors fails Server did not transition to READY state galera_var_node_address : MDEV-20485 Galera test failure galera_var_notify_cmd : MDEV-21905 Galera test galera_var_notify_cmd causes hang +galera_var_notify_ssl_ipv6 : hangs after the merge of MDEV-27682 galera_var_retry_autocommit: MDEV-18181 Galera test failure on galera.galera_var_retry_autocommit partition : MDEV-19958 Galera test failure on galera.partition query_cache: MDEV-15805 Test failure on galera.query_cache -- cgit v1.2.1