Commit 1a6f4704 authored by Marko Mäkelä's avatar Marko Mäkelä

MDEV-19544 Remove innodb_locks_unsafe_for_binlog

The transaction isolation levels READ COMMITTED and READ UNCOMMITTED
should behave similarly to the old deprecated setting
innodb_locks_unsafe_for_binlog=1, that is, avoid acquiring gap locks.

row_search_mvcc(): Reduce the scope of some variables, and clean up
the initialization and use of the variable set_also_gap_locks.
parent 47cede64
......@@ -269,9 +269,6 @@ innodb_autoinc_lock_mode=2
autoinc lock modes 0 and 1 can cause unresolved deadlock, and make
the system unresponsive.
innodb_locks_unsafe_for_binlog=1
This option is required for parallel applying.
5.2 WSREP OPTIONS
All options are optional except for wsrep_provider, wsrep_cluster_address, and
......
......@@ -241,7 +241,6 @@ char* innobase_data_file_path;
my_bool innobase_use_doublewrite;
my_bool innobase_file_per_table;
my_bool innobase_locks_unsafe_for_binlog;
my_bool innobase_rollback_on_timeout;
my_bool innobase_create_status_file;
......@@ -1913,8 +1912,6 @@ static bool innodb_init_param()
srv_file_per_table = (my_bool) innobase_file_per_table;
srv_locks_unsafe_for_binlog = (ibool) innobase_locks_unsafe_for_binlog;
srv_max_n_open_files = ULINT_UNDEFINED - 5;
srv_innodb_status = (ibool) innobase_create_status_file;
......
......@@ -31,20 +31,19 @@ SET SQL_MODE="";
# Show prerequisites for this test.
#
SELECT @@global.tx_isolation;
SELECT @@global.innodb_locks_unsafe_for_binlog;
#
# When innodb_locks_unsafe_for_binlog is not set (zero), which is the
# default, InnoDB takes "next-key locks"/"gap locks". This means it
# With the transaction isolation level REPEATABLE READ (the default)
# or SERIALIZEBLE, InnoDB takes "next-key locks"/"gap locks". This means it
# locks the gap before the keys that it accessed to find the rows to
# use for a statement. In this case we have to expect some more lock
# wait timeouts in the tests below as if innodb_locks_unsafe_for_binlog
# is set (non-zero). In the latter case no "next-key locks"/"gap locks"
# are taken and locks on keys that do not match the WHERE conditon are
# released. Hence less lock collisions occur.
# wait timeouts in the tests, compared to READ UNCOMMITTED or READ COMMITTED.
# For READ UNCOMMITTED or READ COMMITTED, no "next-key locks"/"gap locks"
# are taken and locks on keys that do not match the WHERE condition are
# released. Hence fewer lock collisions occur.
# We use the variable $keep_locks to set the expectations for
# lock wait timeouts accordingly.
#
let $keep_locks= `SELECT NOT @@global.innodb_locks_unsafe_for_binlog`;
let $keep_locks= `SELECT @@global.tx_isolation IN ('REPEATABLE-READ','SERIALIZABLE')`;
--echo # keep_locks == $keep_locks
#
......@@ -52,14 +51,6 @@ let $keep_locks= `SELECT NOT @@global.innodb_locks_unsafe_for_binlog`;
#
GRANT USAGE ON test.* TO mysqltest@localhost;
#
# Preparatory cleanup.
#
--disable_warnings
drop table if exists t1;
--enable_warnings
--echo
--echo **
--echo ** two UPDATE's running and both changing distinct result sets
......@@ -99,7 +90,7 @@ drop table if exists t1;
--echo ** Update on t1 will cause a table scan which will be blocked because
--echo ** the previously initiated table scan applied exclusive key locks on
--echo ** all primary keys.
--echo ** Not so if innodb_locks_unsafe_for_binlog is set. The locks that
--echo ** Not so for READ UNCOMMITTED or READ COMMITTED. The locks that
--echo ** do not match the WHERE condition are released.
if ($keep_locks)
{
......@@ -190,7 +181,7 @@ drop table t1;
--echo ** Update on t1 will cause a table scan which will be blocked because
--echo ** the previously initiated table scan applied exclusive key locks on
--echo ** all primary keys.
--echo ** Not so if innodb_locks_unsafe_for_binlog is set. The locks that
--echo ** Not so for READ UNCOMMITTED or READ COMMITTED. The locks that
--echo ** do not match the WHERE condition are released.
if ($keep_locks)
{
......@@ -386,7 +377,7 @@ drop table t1;
--echo ** Updating single row using a table scan. This will time out
--echo ** because of ongoing transaction on thread 1 holding lock on
--echo ** all primary keys in the scan.
--echo ** Not so if innodb_locks_unsafe_for_binlog is set. The locks that
--echo ** Not so for READ UNCOMMITTED or READ COMMITTED. The locks that
--echo ** do not match the WHERE condition are released.
if ($keep_locks)
{
......@@ -570,7 +561,7 @@ drop table t1;
--echo ** Update on t1 will cause a table scan which will be blocked because
--echo ** the previously initiated table scan applied exclusive key locks on
--echo ** all primary keys.
--echo ** Not so if innodb_locks_unsafe_for_binlog is set. The locks that
--echo ** Not so for READ UNCOMMITTED or READ COMMITTED. The locks that
--echo ** do not match the WHERE condition are released.
if ($keep_locks)
{
......@@ -598,13 +589,8 @@ drop table t1;
connection thread1;
select * from t1;
--echo ** Cleanup
connection thread1;
disconnect thread1;
--source include/wait_until_disconnected.inc
connection thread2;
disconnect thread2;
--source include/wait_until_disconnected.inc
connection default;
drop table t1;
drop user mysqltest@localhost;
......
SET @save_timeout = @@GLOBAL.innodb_lock_wait_timeout;
SET GLOBAL innodb_lock_wait_timeout = 1;
SET GLOBAL TRANSACTION ISOLATION LEVEL REPEATABLE READ;
connection default;
SET SQL_MODE="";
SELECT @@global.tx_isolation;
@@global.tx_isolation
REPEATABLE-READ
SELECT @@global.innodb_locks_unsafe_for_binlog;
@@global.innodb_locks_unsafe_for_binlog
0
# keep_locks == 1
GRANT USAGE ON test.* TO mysqltest@localhost;
drop table if exists t1;
**
** two UPDATE's running and both changing distinct result sets
......@@ -47,7 +45,7 @@ begin;
** Update on t1 will cause a table scan which will be blocked because
** the previously initiated table scan applied exclusive key locks on
** all primary keys.
** Not so if innodb_locks_unsafe_for_binlog is set. The locks that
** Not so for READ UNCOMMITTED or READ COMMITTED. The locks that
** do not match the WHERE condition are released.
update t1 set eta=2 where tipo=22;
ERROR HY000: Lock wait timeout exceeded; try restarting transaction
......@@ -187,7 +185,7 @@ begin;
** Update on t1 will cause a table scan which will be blocked because
** the previously initiated table scan applied exclusive key locks on
** all primary keys.
** Not so if innodb_locks_unsafe_for_binlog is set. The locks that
** Not so for READ UNCOMMITTED or READ COMMITTED. The locks that
** do not match the WHERE condition are released.
update t1 set tipo=1 where tipo=2;
ERROR HY000: Lock wait timeout exceeded; try restarting transaction
......@@ -476,7 +474,7 @@ begin;
** Updating single row using a table scan. This will time out
** because of ongoing transaction on thread 1 holding lock on
** all primary keys in the scan.
** Not so if innodb_locks_unsafe_for_binlog is set. The locks that
** Not so for READ UNCOMMITTED or READ COMMITTED. The locks that
** do not match the WHERE condition are released.
update t1 set tipo=11 where tipo=22;
ERROR HY000: Lock wait timeout exceeded; try restarting transaction
......@@ -736,7 +734,7 @@ begin;
** Update on t1 will cause a table scan which will be blocked because
** the previously initiated table scan applied exclusive key locks on
** all primary keys.
** Not so if innodb_locks_unsafe_for_binlog is set. The locks that
** Not so for READ UNCOMMITTED or READ COMMITTED. The locks that
** do not match the WHERE condition are released.
update t1 set tipo=1 where tipo=22;
ERROR HY000: Lock wait timeout exceeded; try restarting transaction
......@@ -789,12 +787,10 @@ eta tipo c
70 1 iiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiii
80 22 jjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjj
90 11 kkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkk
** Cleanup
connection thread1;
disconnect thread1;
connection thread2;
disconnect thread2;
connection default;
drop table t1;
drop user mysqltest@localhost;
SET SQL_MODE=default;
SET GLOBAL innodb_lock_wait_timeout = @save_timeout;
......@@ -16,8 +16,10 @@
let $engine_type= InnoDB;
SET @save_timeout = @@GLOBAL.innodb_lock_wait_timeout;
SET GLOBAL innodb_lock_wait_timeout = 1;
SET GLOBAL TRANSACTION ISOLATION LEVEL REPEATABLE READ;
# innodb_locks_unsafe_for_binlog not set for this test
--source include/concurrent.inc
SET GLOBAL innodb_lock_wait_timeout = @save_timeout;
--loose-innodb_locks_unsafe_for_binlog
--loose-innodb_lock_wait_timeout=1
SET GLOBAL TRANSACTION ISOLATION LEVEL REPEATABLE READ;
SET @save_timeout = @@GLOBAL.innodb_lock_wait_timeout;
SET GLOBAL innodb_lock_wait_timeout = 1;
SET @save_isolation = @@GLOBAL.tx_isolation;
SET GLOBAL TRANSACTION ISOLATION LEVEL READ COMMITTED;
connection default;
SET SQL_MODE="";
SELECT @@global.tx_isolation;
@@global.tx_isolation
REPEATABLE-READ
SELECT @@global.innodb_locks_unsafe_for_binlog;
@@global.innodb_locks_unsafe_for_binlog
1
READ-COMMITTED
# keep_locks == 0
GRANT USAGE ON test.* TO mysqltest@localhost;
drop table if exists t1;
**
** two UPDATE's running and both changing distinct result sets
......@@ -47,7 +46,7 @@ begin;
** Update on t1 will cause a table scan which will be blocked because
** the previously initiated table scan applied exclusive key locks on
** all primary keys.
** Not so if innodb_locks_unsafe_for_binlog is set. The locks that
** Not so for READ UNCOMMITTED or READ COMMITTED. The locks that
** do not match the WHERE condition are released.
update t1 set eta=2 where tipo=22;
** Release user level name lock from thread 1. This will cause the ULL
......@@ -101,7 +100,7 @@ eta tipo c
60 2 hhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhh
70 1 iiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiii
2 22 jjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjj
90 11 kkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkk
1 11 kkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkk
** And send final commit on thread 1.
commit;
** Table should now be updated by both updates in the order of
......@@ -186,7 +185,7 @@ begin;
** Update on t1 will cause a table scan which will be blocked because
** the previously initiated table scan applied exclusive key locks on
** all primary keys.
** Not so if innodb_locks_unsafe_for_binlog is set. The locks that
** Not so for READ UNCOMMITTED or READ COMMITTED. The locks that
** do not match the WHERE condition are released.
update t1 set tipo=1 where tipo=2;
** Release ULL. This will release the next waiting ULL on thread 2.
......@@ -231,13 +230,13 @@ select * from t1;
eta tipo c
7 7 aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa
8 8 bbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbb
10 1 ccccccccccccccccccccccccccccccccccccccccccc
1 1 ccccccccccccccccccccccccccccccccccccccccccc
20 1 ddddddddddddddddddddddddddddddddddddddddddd
30 1 eeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeee
1 1 eeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeee
40 1 fffffffffffffffffffffffffffffffffffffffffff
50 1 ggggggggggggggggggggggggggggggggggggggggggg
1 1 ggggggggggggggggggggggggggggggggggggggggggg
60 1 hhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhh
70 1 iiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiii
1 1 iiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiii
80 22 jjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjj
90 11 kkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkk
commit;
......@@ -474,7 +473,7 @@ begin;
** Updating single row using a table scan. This will time out
** because of ongoing transaction on thread 1 holding lock on
** all primary keys in the scan.
** Not so if innodb_locks_unsafe_for_binlog is set. The locks that
** Not so for READ UNCOMMITTED or READ COMMITTED. The locks that
** do not match the WHERE condition are released.
update t1 set tipo=11 where tipo=22;
** After the time out the transaction is aborted; no rows should
......@@ -733,7 +732,7 @@ begin;
** Update on t1 will cause a table scan which will be blocked because
** the previously initiated table scan applied exclusive key locks on
** all primary keys.
** Not so if innodb_locks_unsafe_for_binlog is set. The locks that
** Not so for READ UNCOMMITTED or READ COMMITTED. The locks that
** do not match the WHERE condition are released.
update t1 set tipo=1 where tipo=22;
select * from t1;
......@@ -785,12 +784,11 @@ eta tipo c
70 1 iiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiii
80 1 jjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjj
90 11 kkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkk
** Cleanup
connection thread1;
disconnect thread1;
connection thread2;
disconnect thread2;
connection default;
drop table t1;
drop user mysqltest@localhost;
SET SQL_MODE=default;
SET GLOBAL innodb_lock_wait_timeout = @save_timeout;
SET GLOBAL tx_isolation = @save_isolation;
......@@ -16,8 +16,12 @@
let $engine_type= InnoDB;
SET GLOBAL TRANSACTION ISOLATION LEVEL REPEATABLE READ;
# innodb_locks_unsafe_for_binlog is set fro this test.
SET @save_timeout = @@GLOBAL.innodb_lock_wait_timeout;
SET GLOBAL innodb_lock_wait_timeout = 1;
SET @save_isolation = @@GLOBAL.tx_isolation;
SET GLOBAL TRANSACTION ISOLATION LEVEL READ COMMITTED;
--source include/concurrent.inc
SET GLOBAL innodb_lock_wait_timeout = @save_timeout;
SET GLOBAL tx_isolation = @save_isolation;
......@@ -238,8 +238,7 @@ Success: 'show keys from t1' doesn't take row locks on 't1'.
# statement-by-statement) and thanks to MVCC we can always get
# versions of rows prior to the update that has locked them.
# But in practice InnoDB does locking reads for all statements
# other than SELECT (unless it is a READ-COMITTED mode or
# innodb_locks_unsafe_for_binlog is ON).
# other than SELECT (unless READ UNCOMMITTED or READ COMMITTED).
connection default;
Success: 'call p1((select i + 5 from t1 where i = 1))' takes shared row locks on 't1'.
#
......
......@@ -261,8 +261,7 @@ let $statement= show keys from t1;
--echo # statement-by-statement) and thanks to MVCC we can always get
--echo # versions of rows prior to the update that has locked them.
--echo # But in practice InnoDB does locking reads for all statements
--echo # other than SELECT (unless it is a READ-COMITTED mode or
--echo # innodb_locks_unsafe_for_binlog is ON).
--echo # other than SELECT (unless READ UNCOMMITTED or READ COMMITTED).
let $statement= call p1((select i + 5 from t1 where i = 1));
let $wait_statement= $statement;
--source include/check_shared_row_lock.inc
......
--loose-innodb_locks_unsafe_for_binlog --loose-innodb_lock_wait_timeout=1
SET @save_timeout = @@GLOBAL.innodb_lock_wait_timeout;
SET GLOBAL innodb_lock_wait_timeout = 1;
SET @save_isolation = @@GLOBAL.tx_isolation;
SET GLOBAL TRANSACTION ISOLATION LEVEL READ COMMITTED;
drop table if exists t1,t2,t3,t4,t5,t6,t7,t8,t9,t10;
create table t1 (id int not null, f_id int not null, f int not null,
primary key(f_id, id)) engine = InnoDB;
......@@ -187,3 +191,5 @@ disconnect h;
disconnect i;
disconnect j;
drop table t1, t2, t3, t5, t6, t8, t9;
SET GLOBAL innodb_lock_wait_timeout = @save_timeout;
SET GLOBAL tx_isolation = @save_isolation;
......@@ -13,4 +13,12 @@
--source include/have_innodb.inc
let $engine_type= InnoDB;
SET @save_timeout = @@GLOBAL.innodb_lock_wait_timeout;
SET GLOBAL innodb_lock_wait_timeout = 1;
SET @save_isolation = @@GLOBAL.tx_isolation;
SET GLOBAL TRANSACTION ISOLATION LEVEL READ COMMITTED;
--source include/unsafe_binlog.inc
SET GLOBAL innodb_lock_wait_timeout = @save_timeout;
SET GLOBAL tx_isolation = @save_isolation;
......@@ -35,7 +35,6 @@ DROP TABLE t2, t1;
# Bug#46539 Various crashes on INSERT IGNORE SELECT + SELECT
# FOR UPDATE
#
drop table if exists t1;
create table t1 (a int primary key auto_increment,
b int, index(b)) engine=innodb;
insert into t1 (b) values (1), (2), (3), (4), (5), (6), (7), (8), (9), (10);
......@@ -84,19 +83,12 @@ drop table t1, t2;
#
# Bug#41756 Strange error messages about locks from InnoDB
#
drop table if exists t1;
# In the default transaction isolation mode, and/or with
# innodb_locks_unsafe_for_binlog=OFF, handler::unlock_row()
# in InnoDB does nothing.
# In the default transaction isolation mode,
# handler::unlock_row() in InnoDB does nothing.
# Thus in order to reproduce the condition that led to the
# warning, one needs to relax isolation by either
# setting a weaker tx_isolation value, or by turning on
# the unsafe replication switch.
# For testing purposes, choose to tweak the isolation level,
# since it's settable at runtime, unlike
# innodb_locks_unsafe_for_binlog, which is
# only a command-line switch.
#
set @@session.tx_isolation="read-committed";
# Prepare data. We need a table with a unique index,
# for join_read_key to be used. The other column
......
--loose-innodb-locks-unsafe-for-binlog --binlog-format=mixed
--binlog-format=mixed
......@@ -49,9 +49,6 @@ DROP TABLE t2, t1;
--echo # Bug#46539 Various crashes on INSERT IGNORE SELECT + SELECT
--echo # FOR UPDATE
--echo #
--disable_warnings
drop table if exists t1;
--enable_warnings
create table t1 (a int primary key auto_increment,
b int, index(b)) engine=innodb;
insert into t1 (b) values (1), (2), (3), (4), (5), (6), (7), (8), (9), (10);
......@@ -107,21 +104,12 @@ drop table t1, t2;
--echo #
--echo # Bug#41756 Strange error messages about locks from InnoDB
--echo #
--disable_warnings
drop table if exists t1;
--enable_warnings
--echo # In the default transaction isolation mode, and/or with
--echo # innodb_locks_unsafe_for_binlog=OFF, handler::unlock_row()
--echo # in InnoDB does nothing.
--echo # In the default transaction isolation mode,
--echo # handler::unlock_row() in InnoDB does nothing.
--echo # Thus in order to reproduce the condition that led to the
--echo # warning, one needs to relax isolation by either
--echo # setting a weaker tx_isolation value, or by turning on
--echo # the unsafe replication switch.
--echo # For testing purposes, choose to tweak the isolation level,
--echo # since it's settable at runtime, unlike
--echo # innodb_locks_unsafe_for_binlog, which is
--echo # only a command-line switch.
--echo #
set @@session.tx_isolation="read-committed";
--echo # Prepare data. We need a table with a unique index,
......
'#---------------------BS_STVARS_031_01----------------------#'
SELECT COUNT(@@GLOBAL.innodb_locks_unsafe_for_binlog);
COUNT(@@GLOBAL.innodb_locks_unsafe_for_binlog)
1
1 Expected
'#---------------------BS_STVARS_031_02----------------------#'
SET @@GLOBAL.innodb_locks_unsafe_for_binlog=1;
ERROR HY000: Variable 'innodb_locks_unsafe_for_binlog' is a read only variable
Expected error 'Read only variable'
SELECT COUNT(@@GLOBAL.innodb_locks_unsafe_for_binlog);
COUNT(@@GLOBAL.innodb_locks_unsafe_for_binlog)
1
1 Expected
'#---------------------BS_STVARS_031_03----------------------#'
SELECT IF(@@GLOBAL.innodb_locks_unsafe_for_binlog, "ON", "OFF") = VARIABLE_VALUE
FROM INFORMATION_SCHEMA.GLOBAL_VARIABLES
WHERE VARIABLE_NAME='innodb_locks_unsafe_for_binlog';
IF(@@GLOBAL.innodb_locks_unsafe_for_binlog, "ON", "OFF") = VARIABLE_VALUE
1
1 Expected
SELECT COUNT(@@GLOBAL.innodb_locks_unsafe_for_binlog);
COUNT(@@GLOBAL.innodb_locks_unsafe_for_binlog)
1
1 Expected
SELECT COUNT(VARIABLE_VALUE)
FROM INFORMATION_SCHEMA.GLOBAL_VARIABLES
WHERE VARIABLE_NAME='innodb_locks_unsafe_for_binlog';
COUNT(VARIABLE_VALUE)
1
1 Expected
'#---------------------BS_STVARS_031_04----------------------#'
SELECT @@innodb_locks_unsafe_for_binlog = @@GLOBAL.innodb_locks_unsafe_for_binlog;
@@innodb_locks_unsafe_for_binlog = @@GLOBAL.innodb_locks_unsafe_for_binlog
1
1 Expected
'#---------------------BS_STVARS_031_05----------------------#'
SELECT COUNT(@@innodb_locks_unsafe_for_binlog);
COUNT(@@innodb_locks_unsafe_for_binlog)
1
1 Expected
SELECT COUNT(@@local.innodb_locks_unsafe_for_binlog);
ERROR HY000: Variable 'innodb_locks_unsafe_for_binlog' is a GLOBAL variable
Expected error 'Variable is a GLOBAL variable'
SELECT COUNT(@@SESSION.innodb_locks_unsafe_for_binlog);
ERROR HY000: Variable 'innodb_locks_unsafe_for_binlog' is a GLOBAL variable
Expected error 'Variable is a GLOBAL variable'
SELECT COUNT(@@GLOBAL.innodb_locks_unsafe_for_binlog);
COUNT(@@GLOBAL.innodb_locks_unsafe_for_binlog)
1
1 Expected
SELECT innodb_locks_unsafe_for_binlog = @@SESSION.innodb_locks_unsafe_for_binlog;
ERROR 42S22: Unknown column 'innodb_locks_unsafe_for_binlog' in 'field list'
Expected error 'Readonly variable'
......@@ -1324,20 +1324,6 @@ NUMERIC_BLOCK_SIZE 0
ENUM_VALUE_LIST NULL
READ_ONLY NO
COMMAND_LINE_ARGUMENT REQUIRED
VARIABLE_NAME INNODB_LOCKS_UNSAFE_FOR_BINLOG
SESSION_VALUE NULL
GLOBAL_VALUE OFF
GLOBAL_VALUE_ORIGIN COMPILE-TIME
DEFAULT_VALUE OFF
VARIABLE_SCOPE GLOBAL
VARIABLE_TYPE BOOLEAN
VARIABLE_COMMENT DEPRECATED. This option may be removed in future releases. Please use READ COMMITTED transaction isolation level instead. Force InnoDB to not use next-key locking, to use only row-level locking.
NUMERIC_MIN_VALUE NULL
NUMERIC_MAX_VALUE NULL
NUMERIC_BLOCK_SIZE NULL
ENUM_VALUE_LIST OFF,ON
READ_ONLY YES
COMMAND_LINE_ARGUMENT NONE
VARIABLE_NAME INNODB_LOCK_SCHEDULE_ALGORITHM
SESSION_VALUE NULL
GLOBAL_VALUE fcfs
......
################## mysql-test\t\innodb_locks_unsafe_for_binlog_basic.test #####
# #
# Variable Name: innodb_locks_unsafe_for_binlog #
# Scope: Global #
# Access Type: Static #
# Data Type: boolean #
# #
# #
# Creation Date: 2008-02-07 #
# Author : Sharique Abdullah #
# #
# #
# Description:Test Cases of Dynamic System Variable innodb_locks_unsafe_for_binlog#
# that checks the behavior of this variable in the following ways #
# * Value Check #
# * Scope Check #
# #
# Reference: http://dev.mysql.com/doc/refman/5.1/en/ #
# server-system-variables.html #
# #
###############################################################################
--source include/have_innodb.inc
--echo '#---------------------BS_STVARS_031_01----------------------#'
####################################################################
# Displaying default value #
####################################################################
SELECT COUNT(@@GLOBAL.innodb_locks_unsafe_for_binlog);
--echo 1 Expected
--echo '#---------------------BS_STVARS_031_02----------------------#'
####################################################################
# Check if Value can set #
####################################################################
--error ER_INCORRECT_GLOBAL_LOCAL_VAR
SET @@GLOBAL.innodb_locks_unsafe_for_binlog=1;
--echo Expected error 'Read only variable'
SELECT COUNT(@@GLOBAL.innodb_locks_unsafe_for_binlog);
--echo 1 Expected
--echo '#---------------------BS_STVARS_031_03----------------------#'
#################################################################
# Check if the value in GLOBAL Table matches value in variable #
#################################################################
--disable_warnings
SELECT IF(@@GLOBAL.innodb_locks_unsafe_for_binlog, "ON", "OFF") = VARIABLE_VALUE
FROM INFORMATION_SCHEMA.GLOBAL_VARIABLES
WHERE VARIABLE_NAME='innodb_locks_unsafe_for_binlog';
--enable_warnings
--echo 1 Expected
SELECT COUNT(@@GLOBAL.innodb_locks_unsafe_for_binlog);
--echo 1 Expected
--disable_warnings
SELECT COUNT(VARIABLE_VALUE)
FROM INFORMATION_SCHEMA.GLOBAL_VARIABLES
WHERE VARIABLE_NAME='innodb_locks_unsafe_for_binlog';
--enable_warnings
--echo 1 Expected
--echo '#---------------------BS_STVARS_031_04----------------------#'
################################################################################
# Check if accessing variable with and without GLOBAL point to same variable #
################################################################################
SELECT @@innodb_locks_unsafe_for_binlog = @@GLOBAL.innodb_locks_unsafe_for_binlog;
--echo 1 Expected
--echo '#---------------------BS_STVARS_031_05----------------------#'
################################################################################
# Check if innodb_locks_unsafe_for_binlog can be accessed with and without @@ sign #
################################################################################
SELECT COUNT(@@innodb_locks_unsafe_for_binlog);
--echo 1 Expected
--Error ER_INCORRECT_GLOBAL_LOCAL_VAR
SELECT COUNT(@@local.innodb_locks_unsafe_for_binlog);
--echo Expected error 'Variable is a GLOBAL variable'
--Error ER_INCORRECT_GLOBAL_LOCAL_VAR
SELECT COUNT(@@SESSION.innodb_locks_unsafe_for_binlog);
--echo Expected error 'Variable is a GLOBAL variable'
SELECT COUNT(@@GLOBAL.innodb_locks_unsafe_for_binlog);
--echo 1 Expected
--Error ER_BAD_FIELD_ERROR
SELECT innodb_locks_unsafe_for_binlog = @@SESSION.innodb_locks_unsafe_for_binlog;
--echo Expected error 'Readonly variable'
......@@ -4,7 +4,6 @@
[mysqld]
binlog-format=row
innodb-autoinc-lock-mode=2
innodb-locks-unsafe-for-binlog=1
wsrep_provider=@ENV.WSREP_PROVIDER
[mysqld.1]
......
This diff is collapsed.
......@@ -200,7 +200,6 @@ static char* innobase_server_stopword_table;
values */
static my_bool innobase_use_atomic_writes;
static my_bool innobase_locks_unsafe_for_binlog;
static my_bool innobase_rollback_on_timeout;
static my_bool innobase_create_status_file;
my_bool innobase_stats_on_metadata;
......@@ -3979,14 +3978,6 @@ static int innodb_init_params()
row_rollback_on_timeout = (ibool) innobase_rollback_on_timeout;
srv_locks_unsafe_for_binlog = (ibool) innobase_locks_unsafe_for_binlog;
if (innobase_locks_unsafe_for_binlog) {
ib::warn() << "Using innodb_locks_unsafe_for_binlog is"
" DEPRECATED. This option may be removed in future"
" releases. Please use READ COMMITTED transaction"
" isolation level instead; " << SET_TRANSACTION_MSG;
}
if (innobase_open_files < 10) {
innobase_open_files = 300;
if (srv_file_per_table && tc_size > 300 && tc_size < open_files_limit) {
......@@ -9011,7 +9002,7 @@ ha_innobase::delete_all_rows()
/**********************************************************************//**
Removes a new lock set on a row, if it was not read optimistically. This can
be called after a row has been read in the processing of an UPDATE or a DELETE
query, if the option innodb_locks_unsafe_for_binlog is set. */
query. */
void
ha_innobase::unlock_row(void)
......@@ -9027,11 +9018,8 @@ ha_innobase::unlock_row(void)
switch (m_prebuilt->row_read_type) {
case ROW_READ_WITH_LOCKS:
if (!srv_locks_unsafe_for_binlog
&& m_prebuilt->trx->isolation_level
> TRX_ISO_READ_COMMITTED) {
if (m_prebuilt->trx->isolation_level > TRX_ISO_READ_COMMITTED)
break;
}
/* fall through */
case ROW_READ_TRY_SEMI_CONSISTENT:
row_unlock_for_mysql(m_prebuilt, FALSE);
......@@ -9054,28 +9042,16 @@ ha_innobase::was_semi_consistent_read(void)
}
/* See handler.h and row0mysql.h for docs on this function. */
void
ha_innobase::try_semi_consistent_read(bool yes)
/*===========================================*/
void ha_innobase::try_semi_consistent_read(bool yes)
{
ut_a(m_prebuilt->trx == thd_to_trx(ha_thd()));
ut_ad(m_prebuilt->trx == thd_to_trx(ha_thd()));
/* Row read type is set to semi consistent read if this was
requested by the MySQL and either innodb_locks_unsafe_for_binlog
option is used or this session is using READ COMMITTED isolation
level. */
if (yes
&& (srv_locks_unsafe_for_binlog
|| m_prebuilt->trx->isolation_level
<= TRX_ISO_READ_COMMITTED)) {
m_prebuilt->row_read_type = ROW_READ_TRY_SEMI_CONSISTENT;
} else {
m_prebuilt->row_read_type = ROW_READ_WITH_LOCKS;
}
requested by the SQL layer and the transaction isolation level is
READ UNCOMMITTED or READ COMMITTED. */
m_prebuilt->row_read_type = yes
&& m_prebuilt->trx->isolation_level <= TRX_ISO_READ_COMMITTED
? ROW_READ_TRY_SEMI_CONSISTENT
: ROW_READ_WITH_LOCKS;
}
/******************************************************************//**
......@@ -16347,9 +16323,7 @@ ha_innobase::store_lock(
if (sql_command == SQLCOM_CHECKSUM
|| sql_command == SQLCOM_CREATE_SEQUENCE
|| (sql_command == SQLCOM_ANALYZE && lock_type == TL_READ)
|| ((srv_locks_unsafe_for_binlog
|| trx->isolation_level <= TRX_ISO_READ_COMMITTED)
&& trx->isolation_level != TRX_ISO_SERIALIZABLE
|| (trx->isolation_level <= TRX_ISO_READ_COMMITTED
&& (lock_type == TL_READ
|| lock_type == TL_READ_NO_INSERT)
&& (sql_command == SQLCOM_INSERT_SELECT
......@@ -16358,10 +16332,8 @@ ha_innobase::store_lock(
|| sql_command == SQLCOM_CREATE_SEQUENCE
|| sql_command == SQLCOM_CREATE_TABLE))) {
/* If we either have innobase_locks_unsafe_for_binlog
option set or this session is using READ COMMITTED
isolation level and isolation level of the transaction
is not set to serializable and MySQL is doing
/* If the transaction isolation level is
READ UNCOMMITTED or READ COMMITTED and we are executing
INSERT INTO...SELECT or REPLACE INTO...SELECT
or UPDATE ... = (SELECT ...) or CREATE ...
SELECT... without FOR UPDATE or IN SHARE
......@@ -18914,13 +18886,6 @@ static MYSQL_SYSVAR_BOOL(force_load_corrupted, srv_load_corrupted,
"Force InnoDB to load metadata of corrupted table.",
NULL, NULL, FALSE);
static MYSQL_SYSVAR_BOOL(locks_unsafe_for_binlog, innobase_locks_unsafe_for_binlog,
PLUGIN_VAR_NOCMDARG | PLUGIN_VAR_READONLY,
"DEPRECATED. This option may be removed in future releases."
" Please use READ COMMITTED transaction isolation level instead."
" Force InnoDB to not use next-key locking, to use only row-level locking.",
NULL, NULL, FALSE);
static MYSQL_SYSVAR_STR(log_group_home_dir, srv_log_group_home_dir,
PLUGIN_VAR_RQCMDARG | PLUGIN_VAR_READONLY,
"Path to InnoDB log files.", NULL, NULL, NULL);
......@@ -19969,7 +19934,6 @@ static struct st_mysql_sys_var* innobase_system_variables[]= {
MYSQL_SYSVAR(large_prefix), /* deprecated in MariaDB 10.2; no effect */
MYSQL_SYSVAR(force_load_corrupted),
MYSQL_SYSVAR(lock_schedule_algorithm),
MYSQL_SYSVAR(locks_unsafe_for_binlog),
MYSQL_SYSVAR(lock_wait_timeout),
MYSQL_SYSVAR(deadlock_detect),
MYSQL_SYSVAR(page_size),
......
......@@ -271,8 +271,8 @@ row_update_for_mysql(
row_prebuilt_t* prebuilt)
MY_ATTRIBUTE((warn_unused_result));
/** This can only be used when srv_locks_unsafe_for_binlog is TRUE or this
session is using a READ COMMITTED or READ UNCOMMITTED isolation level.
/** This can only be used when the current transaction is at
READ COMMITTED or READ UNCOMMITTED isolation level.
Before calling this function row_search_for_mysql() must have
initialized prebuilt->new_rec_locks to store the information which new
record locks really were set. This function removes a newly set
......@@ -694,8 +694,9 @@ struct row_prebuilt_t {
ulint row_read_type; /*!< ROW_READ_WITH_LOCKS if row locks
should be the obtained for records
under an UPDATE or DELETE cursor.
If innodb_locks_unsafe_for_binlog
is TRUE, this can be set to
At READ UNCOMMITTED or
READ COMMITTED isolation level,
this can be set to
ROW_READ_TRY_SEMI_CONSISTENT, so that
if the row under an UPDATE or DELETE
cursor was locked by another
......@@ -717,8 +718,7 @@ struct row_prebuilt_t {
cases; note that this breaks
serializability. */
ulint new_rec_locks; /*!< normally 0; if
srv_locks_unsafe_for_binlog is
TRUE or session is using READ
the session is using READ
COMMITTED or READ UNCOMMITTED
isolation level, set in
row_search_for_mysql() if we set a new
......
......@@ -3,7 +3,7 @@
Copyright (c) 1995, 2017, Oracle and/or its affiliates. All rights reserved.
Copyright (c) 2008, 2009, Google Inc.
Copyright (c) 2009, Percona Inc.
Copyright (c) 2013, 2018, MariaDB Corporation.
Copyright (c) 2013, 2019, MariaDB Corporation.
Portions of this file contain modifications contributed and copyrighted by
Google, Inc. Those modifications are gratefully acknowledged and are described
......@@ -254,10 +254,6 @@ extern ulong srv_thread_sleep_delay;
/** Maximum sleep delay (in micro-seconds), value of 0 disables it.*/
extern ulong srv_adaptive_max_sleep_delay;
/** Place locks to records only i.e. do not use next-key locking except
on duplicate key checking and foreign key checking */
extern ibool srv_locks_unsafe_for_binlog;
/** Sort buffer size in index creation */
extern ulong srv_sort_buf_size;
/** Maximum modification log file size for online index creation */
......
......@@ -2436,8 +2436,8 @@ lock_rec_inherit_to_gap(
ut_ad(lock_mutex_own());
/* If srv_locks_unsafe_for_binlog is TRUE or session is using
READ COMMITTED isolation level, we do not want locks set
/* At READ UNCOMMITTED or READ COMMITTED isolation level,
we do not want locks set
by an UPDATE or a DELETE to be inherited as gap type locks. But we
DO want S-locks/X-locks(taken for replace) set by a consistency
constraint to be inherited also then. */
......@@ -2447,11 +2447,9 @@ lock_rec_inherit_to_gap(
lock = lock_rec_get_next(heap_no, lock)) {
if (!lock_rec_get_insert_intention(lock)
&& !((srv_locks_unsafe_for_binlog
|| lock->trx->isolation_level
<= TRX_ISO_READ_COMMITTED)
&& lock_get_mode(lock) ==
(lock->trx->duplicates ? LOCK_S : LOCK_X))) {
&& (lock->trx->isolation_level > TRX_ISO_READ_COMMITTED
|| lock_get_mode(lock) !=
(lock->trx->duplicates ? LOCK_S : LOCK_X))) {
lock_rec_add_to_queue(
LOCK_REC | LOCK_GAP
| ulint(lock_get_mode(lock)),
......
......@@ -1979,8 +1979,8 @@ row_update_for_mysql(row_prebuilt_t* prebuilt)
DBUG_RETURN(err);
}
/** This can only be used when srv_locks_unsafe_for_binlog is TRUE or this
session is using a READ COMMITTED or READ UNCOMMITTED isolation level.
/** This can only be used when the current transaction is at
READ COMMITTED or READ UNCOMMITTED isolation level.
Before calling this function row_search_for_mysql() must have
initialized prebuilt->new_rec_locks to store the information which new
record locks really were set. This function removes a newly set
......@@ -2003,17 +2003,8 @@ row_unlock_for_mysql(
ut_ad(prebuilt != NULL);
ut_ad(trx != NULL);
ut_ad(trx->isolation_level <= TRX_ISO_READ_COMMITTED);
if (UNIV_UNLIKELY
(!srv_locks_unsafe_for_binlog
&& trx->isolation_level > TRX_ISO_READ_COMMITTED)) {
ib::error() << "Calling row_unlock_for_mysql though"
" innodb_locks_unsafe_for_binlog is FALSE and this"
" session is not using READ COMMITTED isolation"
" level.";
return;
}
if (dict_index_is_spatial(prebuilt->index)) {
return;
}
......
This diff is collapsed.
......@@ -148,9 +148,6 @@ my_bool srv_file_per_table;
is greater than SRV_FORCE_NO_TRX_UNDO. */
my_bool high_level_read_only;
/** Place locks to records only i.e. do not use next-key locking except
on duplicate key checking and foreign key checking */
ibool srv_locks_unsafe_for_binlog;
/** Sort buffer size in index creation */
ulong srv_sort_buf_size;
/** Maximum modification log file size for online index creation */
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment