Skip to content

Commit

Permalink
Add range locking support for MyRocks
Browse files Browse the repository at this point in the history
- Add new sysvar, rocksdb_use_range_locking. When it's on:
- RocksDB is initialized to used range-locking lock manager
- For all DML operations (including SELECT ... FOR UPDATE), the scanned range
  will be locked before reading/modifying rows
- For all DML operations, MyRocks will read and modify the latest committed
  data, just like InnoDB does, because there is no snapshot checking if range
  locking is used.
- Introduce a RocksDB locking iterator, which reads the rows, locks the range,
- and re-reads the rows. It is used for queries that do not have a finite range
  to scan, like UPDATE t1 ... ORDER BY t1.key LIMIT n
- Add another new sysvar, rocksdb_use_range_lock_manager_as_point, which uses
  the point locking algorithm but the lock manager used is the range one.
- Add enabled rocksdb_use_range_locking as another MTR rocksdb suite test
  combination.

Co-authored-by: Sergei Petrunia <[email protected]>
Co-authored-by: Laurynas Biveinis <[email protected]>
  • Loading branch information
laurynas-biveinis and spetrunia committed Apr 26, 2024
1 parent 4874647 commit 6f3cc1f
Show file tree
Hide file tree
Showing 91 changed files with 7,654 additions and 117 deletions.
10 changes: 10 additions & 0 deletions mysql-test/r/mysqld--help-notwin.result
Original file line number Diff line number Diff line change
Expand Up @@ -2337,6 +2337,9 @@ The following options may be given as the first argument:
and newtransaction will be started.
--rocksdb-max-latest-deadlocks=#
Maximum number of recent deadlocks to store
--rocksdb-max-lock-memory=#
Range-locking mode: Maximum amount of memory that locks
from all transactions can use at a time
--rocksdb-max-log-file-size=#
DBOptions::max_log_file_size for RocksDB
--rocksdb-max-manifest-file-size=#
Expand Down Expand Up @@ -2575,6 +2578,10 @@ The following options may be given as the first argument:
RocksDB
--rocksdb-use-io-uring
Use io_uring for RocksDB
--rocksdb-use-range-lock-manager-as-point
Use Range Lock Manager as point
--rocksdb-use-range-locking
Use Range Locking
--rocksdb-use-write-buffer-manager
For experiment only. Use write buffer manager
--rocksdb-validate-tables=#
Expand Down Expand Up @@ -3911,6 +3918,7 @@ rocksdb-max-compaction-history 64
rocksdb-max-file-opening-threads 16
rocksdb-max-intrinsic-tmp-table-write-count 1000
rocksdb-max-latest-deadlocks 5
rocksdb-max-lock-memory 1073741824
rocksdb-max-log-file-size 0
rocksdb-max-manifest-file-size 1073741824
rocksdb-max-manual-compactions 10
Expand Down Expand Up @@ -3990,6 +3998,8 @@ rocksdb-use-direct-reads FALSE
rocksdb-use-fsync FALSE
rocksdb-use-hyper-clock-cache FALSE
rocksdb-use-io-uring FALSE
rocksdb-use-range-lock-manager-as-point FALSE
rocksdb-use-range-locking FALSE
rocksdb-use-write-buffer-manager FALSE
rocksdb-validate-tables 1
rocksdb-vector-index ON
Expand Down
3 changes: 3 additions & 0 deletions mysql-test/suite/rocksdb/combinations
Original file line number Diff line number Diff line change
Expand Up @@ -2,3 +2,6 @@

[rocksdb_ddse]
default_dd_system_storage_engine = rocksdb

[range_locking]
rocksdb_use_range_locking=1
3 changes: 3 additions & 0 deletions mysql-test/suite/rocksdb/include/have_range_locking.inc
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
if (`select count(*) = 0 from performance_schema.session_variables where variable_name = 'rocksdb_use_range_locking' and variable_value = 'ON';`) {
--skip Test requires range locking
}
5 changes: 5 additions & 0 deletions mysql-test/suite/rocksdb/include/not_range_locking.inc
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
--let $_use_range_locking= `select @@rocksdb_use_range_locking`
if ($_use_range_locking == 1)
{
--skip Test doesn't support range locking
}
99 changes: 99 additions & 0 deletions mysql-test/suite/rocksdb/include/select_from_is_rowlocks.inc
Original file line number Diff line number Diff line change
@@ -0,0 +1,99 @@
--echo # select * from information_schema.rocksdb_locks; # With replacements by select_from_is_rowlocks.inc
#
# An include to print contents of I_S.ROCKSB_LOCKS
#
# Implicit "parameters"
# - Currently it prints locks on t1.PRIMARY
#
# Explicit "parameter" variables:
# - $TRX1_ID - print this transaction as "TRX1"
# - $TRX2_ID - print this transaction as "TRX2"
#
# - $select_from_is_rowlocks_current_trx_only
# - $order_by_rowkey
#
# - $SECOND_INDEX_NAME

--disable_query_log
set @cf_id=(select column_family from information_schema.rocksdb_ddl
where table_name='t1' and index_name='PRIMARY');
set @rtrx_id=(select transaction_id from information_schema.rocksdb_trx
where thread_id=connection_id());
set @indexnr= (select lower(lpad(hex(index_number),8,'0')) from information_schema.rocksdb_ddl
where table_name='t1' and index_name='PRIMARY');

set @indexnr_next= (select lower(lpad(hex(index_number+1),8,'0'))
from information_schema.rocksdb_ddl
where table_name='t1' and index_name='PRIMARY');

let $extra_where = where 1;

if ($select_from_is_rowlocks_current_trx_only)
{
let $extra_where = where transaction_id=(select transaction_id from information_schema.rocksdb_trx where connection_id()=thread_id);
}

## transaction column

# If TRX1_ID is not specified, get the current transaction:
let $transaction_col= replace(transaction_id, @rtrx_id, "\$trx_id");
if ($TRX1_ID)
{
let $transaction_col = replace(transaction_id, '$TRX1_ID', "\$TRX1_ID");
}

if ($TRX2_ID)
{
let $transaction_col = replace($transaction_col, '$TRX2_ID', "\$TRX2_ID");
}

## CF_ID column
let $cf_id_col= column_family_id;

if ($SECOND_INDEX_NAME)
{
eval set @cf2_id=(select column_family from information_schema.rocksdb_ddl
where table_name='t1' and index_name='$SECOND_INDEX_NAME');

let $cf_id_col= replace($cf_id_col, @cf2_id, "\$cf2_id");
}
let $cf_id_col= replace($cf_id_col, @cf_id, "\$cf_id");

## KEY column
let $key_col= (`key`);
if ($SECOND_INDEX_NAME)
{
eval set @indexnr2= (select lower(lpad(hex(index_number),8,'0'))
from information_schema.rocksdb_ddl
where table_name='t1' and index_name='$SECOND_INDEX_NAME');

eval set @indexnr2_next= (select lower(lpad(hex(index_number+1),8,'0'))
from information_schema.rocksdb_ddl
where table_name='t1' and index_name='$SECOND_INDEX_NAME');

let $key_col = replace($key_col, @indexnr2, '\${indexnr2}');
let $key_col = replace($key_col, @indexnr2_next, '\${indexnr2+1}');
}

let $key_col = replace($key_col, @indexnr, '\${indexnr}');
let $key_col = replace($key_col, @indexnr_next, '\${indexnr+1}');

## ORDER BY
if ($order_by_rowkey)
{
let $extra_order_by = ORDER BY 3,2;
}

if (!$order_by_rowkey)
{
--sorted_result
}

eval select
$cf_id_col as COLUMN_FAMILY_ID,
$transaction_col as TRANSACTION_ID,
$key_col as `KEY`,
mode
from information_schema.rocksdb_locks $extra_where $extra_order_by;

--enable_query_log
Loading

0 comments on commit 6f3cc1f

Please sign in to comment.