github.com/matrixorigin/matrixone@v0.7.0/pkg/lockservice/types.go (about)

     1  // Copyright 2022 Matrix Origin
     2  //
     3  // Licensed under the Apache License, Version 2.0 (the "License");
     4  // you may not use this file except in compliance with the License.
     5  // You may obtain a copy of the License at
     6  //
     7  //      http://www.apache.org/licenses/LICENSE-2.0
     8  //
     9  // Unless required by applicable law or agreed to in writing, software
    10  // distributed under the License is distributed on an "AS IS" BASIS,
    11  // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
    12  // See the License for the specific language governing permissions and
    13  // limitations under the License.
    14  
    15  package lockservice
    16  
    17  import (
    18  	"context"
    19  )
    20  
    21  // Granularity row granularity, single row or row range
    22  type Granularity int
    23  
    24  const (
    25  	// Row single row
    26  	Row Granularity = iota
    27  	// Range row range mode
    28  	Range
    29  )
    30  
    31  // LockMode exclusive or shared lock
    32  type LockMode int
    33  
    34  const (
    35  	// Exclusive mode
    36  	Exclusive LockMode = iota
    37  	// Shared mode
    38  	Shared
    39  )
    40  
    41  // WaitPolicy waiting strategy if lock conflicts are encountered when locking.
    42  type WaitPolicy int
    43  
    44  const (
    45  	// Wait waiting for conflicting locks to be released
    46  	Wait WaitPolicy = iota
    47  	// FastFail return fail if lock conflicts are encountered
    48  	FastFail
    49  )
    50  
    51  // LockStorage the store that holds the locks, a storage instance is corresponding to
    52  // all the locks of a table. The LockStorage no need to be thread-safe.
    53  //
    54  // All locks are stored in an orderly in the LockStorage, so lock conflicts
    55  // can be easily detected.
    56  type LockStorage interface {
    57  	// Add we use kv to store the lock. Key is a locked row or a row range. Value is the
    58  	// TxnID.
    59  	Add(key []byte, value Lock)
    60  	// Get returns the value of the given key
    61  	Get(key []byte) (Lock, bool)
    62  	// Len returns number of the locks in the storage
    63  	Len() int
    64  	// Delete delete lock from the storage
    65  	Delete(key []byte)
    66  	// Seek returns the first KV Pair that is >= the given key
    67  	Seek(key []byte) ([]byte, Lock, bool)
    68  }
    69  
    70  // LockService lock service is running at the CN node. The lockservice maintains a set
    71  // of LockStorage internally (one table corresponds to one LockStorage instance).
    72  // All Lock and Unlock operations on each Table are concurrent.
    73  //
    74  // Lock waiting is implemented as fair, internally there is a waiting queue for each
    75  // Lock and when a Lock is released, a new Lock is executed in a FIFO fashion. And the
    76  // element in the wait queue is the transaction ID.
    77  //
    78  // The current lock waiting mechanism will trigger deadlock, so lockservice has implemented
    79  // a deadlock detection mechanism internally. In order to ensure the performance of Lock
    80  // operations, we cannot synchronise deadlock detection with each Lock operation.
    81  // The current implementation is that when a new waiter is added to the wait queue of any
    82  // Lock, a set of background goroutines are notified to start a deadlock detection for all
    83  // transactions in the Lock's wait queue.
    84  type LockService interface {
    85  	// Lock locks rows(row or row range determined by the Granularity in options) a table. Lockservice
    86  	// has no requirement for the format of rows, but requires all rows of a table on a lockservice
    87  	// to be sortable.
    88  	//
    89  	// If a conflict is encountered, the method will block until the conflicting lock is
    90  	// released and held by the current operation, or until it times out.
    91  	//
    92  	// Returns false if conflicts are encountered in FastFail wait policy and ErrDeadLockDetected
    93  	// returns if current operation was aborted by deadlock detection.
    94  	Lock(ctx context.Context, tableID uint64, rows [][]byte, txnID []byte, options LockOptions) error
    95  	// Unlock release all locks associated with the transaction.
    96  	Unlock(txnID []byte) error
    97  	// Close close the lock service.
    98  	Close() error
    99  }
   100  
   101  // LockOptions options for lock
   102  type LockOptions struct {
   103  	granularity Granularity
   104  	mode        LockMode
   105  	policy      WaitPolicy
   106  }
   107  
   108  // Lock stores specific lock information. Since there are a large number of lock objects
   109  // in the LockStorage at runtime, this object has been specially designed to save memory
   110  // usage.
   111  type Lock struct {
   112  	txnID []byte
   113  	// all lock info will encode into this field to save memory overhead
   114  	value  byte
   115  	waiter *waiter
   116  }