diff options
author | Thirunarayanan Balathandayuthapani <thiru@mariadb.com> | 2023-03-24 15:20:21 +0530 |
---|---|---|
committer | Thirunarayanan Balathandayuthapani <thiru@mariadb.com> | 2023-03-24 15:20:21 +0530 |
commit | e06c6046d25052d8ad7a8c1f72ea666bc983c674 (patch) | |
tree | 3c98a7a5086f9c9cb6c97484cf5c15d666059eef | |
parent | 07460c31e30cc1f6b56dab6e9a54a7618e26050b (diff) | |
download | mariadb-git-e06c6046d25052d8ad7a8c1f72ea666bc983c674.tar.gz |
MDEV-29545 InnoDB: Can't find record during replace stmt
Problem:
========
- InnoDB replace statement returns can't find record as result during
bulk insert operation. InnoDB returns DB_END_OF_INDEX blindly when
bulk transaction is visible to current transaction even though
the search tuple is inserted as a part of current replace statement.
Solution:
=========
row_search_mvcc(): InnoDB should allow the transaction to read
all the rows when innodb intends to do any locking on the
record even though bulk insert transaction changes are
visible to the current transaction
-rw-r--r-- | mysql-test/suite/innodb/r/insert_into_empty.result | 22 | ||||
-rw-r--r-- | mysql-test/suite/innodb/t/insert_into_empty.test | 22 | ||||
-rw-r--r-- | storage/innobase/row/row0sel.cc | 6 |
3 files changed, 49 insertions, 1 deletions
diff --git a/mysql-test/suite/innodb/r/insert_into_empty.result b/mysql-test/suite/innodb/r/insert_into_empty.result index 25cc489bdab..ef7d015f7f3 100644 --- a/mysql-test/suite/innodb/r/insert_into_empty.result +++ b/mysql-test/suite/innodb/r/insert_into_empty.result @@ -229,4 +229,26 @@ commit; SELECT * FROM t; c DROP TABLE t; +# +# MDEV-29545 InnoDB: Can't find record during replace stmt +# +CREATE TABLE t1(c1 INT PRIMARY KEY)ENGINE=InnoDB; +BEGIN; +INSERT INTO t1 VALUES(3331); +connect con1,localhost,root,,,; +BEGIN; +SELECT c1 FROM t1; +c1 +connection default; +COMMIT; +connection con1; +REPLACE INTO t1 VALUES(1984), (1984); +COMMIT; +connection default; +disconnect con1; +SELECT * FROM t1; +c1 +1984 +3331 +DROP TABLE t1; # End of 10.6 tests diff --git a/mysql-test/suite/innodb/t/insert_into_empty.test b/mysql-test/suite/innodb/t/insert_into_empty.test index 932ab4c2a23..010b7ecb43a 100644 --- a/mysql-test/suite/innodb/t/insert_into_empty.test +++ b/mysql-test/suite/innodb/t/insert_into_empty.test @@ -247,4 +247,26 @@ SAVEPOINT a; commit; SELECT * FROM t; DROP TABLE t; + +--echo # +--echo # MDEV-29545 InnoDB: Can't find record during replace stmt +--echo # +CREATE TABLE t1(c1 INT PRIMARY KEY)ENGINE=InnoDB; +BEGIN; +INSERT INTO t1 VALUES(3331); + +connect(con1,localhost,root,,,); +BEGIN; +SELECT c1 FROM t1; + +connection default; +COMMIT; + +connection con1; +REPLACE INTO t1 VALUES(1984), (1984); +COMMIT; +connection default; +disconnect con1; +SELECT * FROM t1; +DROP TABLE t1; --echo # End of 10.6 tests diff --git a/storage/innobase/row/row0sel.cc b/storage/innobase/row/row0sel.cc index e44cc466295..d1d264a7e8a 100644 --- a/storage/innobase/row/row0sel.cc +++ b/storage/innobase/row/row0sel.cc @@ -4892,7 +4892,11 @@ page_corrupted: if (trx->isolation_level == TRX_ISO_READ_UNCOMMITTED || !trx->read_view.is_open()) { } else if (trx_id_t bulk_trx_id = index->table->bulk_trx_id) { - if (!trx->read_view.changes_visible(bulk_trx_id)) { + /* InnoDB should allow the transaction to read all + the rows when InnoDB intends to do any locking + on the record */ + if (prebuilt->select_lock_type == LOCK_NONE + && !trx->read_view.changes_visible(bulk_trx_id)) { trx->op_info = ""; err = DB_END_OF_INDEX; goto normal_return; |