From 31dffd10c0ebbc791ea53bf959718cd0d9d2658e Mon Sep 17 00:00:00 2001 From: unknown Date: Wed, 25 Jul 2007 13:29:57 -0600 Subject: [PATCH] Apply snapshot innodb-51-ss1644: Part #2. I forgot to check in some new files: lock0priv.h lock0priv.ic lock0iter.c lock0iter.h storage/innobase/include/lock0iter.h: BitKeeper file /home/tsmith/m/bk/inno/jul24/51/storage/innobase/include/lock0iter.h storage/innobase/include/lock0priv.h: BitKeeper file /home/tsmith/m/bk/inno/jul24/51/storage/innobase/include/lock0priv.h storage/innobase/include/lock0priv.ic: BitKeeper file /home/tsmith/m/bk/inno/jul24/51/storage/innobase/include/lock0priv.ic storage/innobase/lock/lock0iter.c: BitKeeper file /home/tsmith/m/bk/inno/jul24/51/storage/innobase/lock/lock0iter.c --- storage/innobase/include/lock0iter.h | 52 +++++++++++++ storage/innobase/include/lock0priv.h | 101 ++++++++++++++++++++++++++ storage/innobase/include/lock0priv.ic | 32 ++++++++ storage/innobase/lock/lock0iter.c | 91 +++++++++++++++++++++++ 4 files changed, 276 insertions(+) create mode 100644 storage/innobase/include/lock0iter.h create mode 100644 storage/innobase/include/lock0priv.h create mode 100644 storage/innobase/include/lock0priv.ic create mode 100644 storage/innobase/lock/lock0iter.c diff --git a/storage/innobase/include/lock0iter.h b/storage/innobase/include/lock0iter.h new file mode 100644 index 00000000000..d063a360c1f --- /dev/null +++ b/storage/innobase/include/lock0iter.h @@ -0,0 +1,52 @@ +/****************************************************** +Lock queue iterator type and function prototypes. + +(c) 2007 Innobase Oy + +Created July 16, 2007 Vasil Dimov +*******************************************************/ + +#ifndef lock0iter_h +#define lock0iter_h + +#include "univ.i" +#include "lock0types.h" + +typedef struct lock_queue_iterator_struct { + lock_t* current_lock; + /* In case this is a record lock queue (not table lock queue) + then bit_no is the record number within the heap in which the + record is stored. */ + ulint bit_no; +} lock_queue_iterator_t; + +/*********************************************************************** +Initialize lock queue iterator so that it starts to iterate from +"lock". bit_no specifies the record number within the heap where the +record is stored. It can be undefined (ULINT_UNDEFINED) in two cases: +1. If the lock is a table lock, thus we have a table lock queue; +2. If the lock is a record lock and it is a wait lock. In this case + bit_no is calculated in this function by using + lock_rec_find_set_bit(). There is exactly one bit set in the bitmap + of a wait lock. */ + +void +lock_queue_iterator_reset( +/*======================*/ + lock_queue_iterator_t* iter, /* out: iterator */ + lock_t* lock, /* in: lock to start from */ + ulint bit_no);/* in: record number in the + heap */ + +/*********************************************************************** +Gets the previous lock in the lock queue, returns NULL if there are no +more locks (i.e. the current lock is the first one). The iterator is +receded (if not-NULL is returned). */ + +lock_t* +lock_queue_iterator_get_prev( +/*=========================*/ + /* out: previous lock or NULL */ + lock_queue_iterator_t* iter); /* in/out: iterator */ + +#endif /* lock0iter_h */ diff --git a/storage/innobase/include/lock0priv.h b/storage/innobase/include/lock0priv.h new file mode 100644 index 00000000000..7703a2b7def --- /dev/null +++ b/storage/innobase/include/lock0priv.h @@ -0,0 +1,101 @@ +/****************************************************** +Lock module internal structures and methods. + +(c) 2007 Innobase Oy + +Created July 12, 2007 Vasil Dimov +*******************************************************/ + +#ifndef lock0priv_h +#define lock0priv_h + +#ifndef LOCK_MODULE_IMPLEMENTATION +/* If you need to access members of the structures defined in this +file, please write appropriate functions that retrieve them and put +those functions in lock/ */ +#error Do not include lock0priv.h outside of the lock/ module +#endif + +#include "univ.i" +#include "dict0types.h" +#include "hash0hash.h" +#include "trx0types.h" +#include "ut0lst.h" + +/* A table lock */ +typedef struct lock_table_struct lock_table_t; +struct lock_table_struct { + dict_table_t* table; /* database table in dictionary + cache */ + UT_LIST_NODE_T(lock_t) + locks; /* list of locks on the same + table */ +}; + +/* Record lock for a page */ +typedef struct lock_rec_struct lock_rec_t; +struct lock_rec_struct { + ulint space; /* space id */ + ulint page_no; /* page number */ + ulint n_bits; /* number of bits in the lock + bitmap; NOTE: the lock bitmap is + placed immediately after the + lock struct */ +}; + +/* Lock struct */ +struct lock_struct { + trx_t* trx; /* transaction owning the + lock */ + UT_LIST_NODE_T(lock_t) + trx_locks; /* list of the locks of the + transaction */ + ulint type_mode; /* lock type, mode, LOCK_GAP or + LOCK_REC_NOT_GAP, + LOCK_INSERT_INTENTION, + wait flag, ORed */ + hash_node_t hash; /* hash chain node for a record + lock */ + dict_index_t* index; /* index for a record lock */ + union { + lock_table_t tab_lock;/* table lock */ + lock_rec_t rec_lock;/* record lock */ + } un_member; +}; + +/************************************************************************* +Gets the type of a lock. */ +UNIV_INLINE +ulint +lock_get_type( +/*==========*/ + /* out: LOCK_TABLE or LOCK_REC */ + const lock_t* lock); /* in: lock */ + +/************************************************************************** +Looks for a set bit in a record lock bitmap. Returns ULINT_UNDEFINED, +if none found. */ + +ulint +lock_rec_find_set_bit( +/*==================*/ + /* out: bit index == heap number of the record, or + ULINT_UNDEFINED if none found */ + lock_t* lock); /* in: record lock with at least one bit set */ + +/************************************************************************* +Gets the previous record lock set on a record. */ + +lock_t* +lock_rec_get_prev( +/*==============*/ + /* out: previous lock on the same record, NULL if + none exists */ + lock_t* in_lock,/* in: record lock */ + ulint heap_no);/* in: heap number of the record */ + +#ifndef UNIV_NONINL +#include "lock0priv.ic" +#endif + +#endif /* lock0priv_h */ diff --git a/storage/innobase/include/lock0priv.ic b/storage/innobase/include/lock0priv.ic new file mode 100644 index 00000000000..4bc8397509d --- /dev/null +++ b/storage/innobase/include/lock0priv.ic @@ -0,0 +1,32 @@ +/****************************************************** +Lock module internal inline methods. + +(c) 2007 Innobase Oy + +Created July 16, 2007 Vasil Dimov +*******************************************************/ + +/* This file contains only methods which are used in +lock/lock0* files, other than lock/lock0lock.c. +I.e. lock/lock0lock.c contains more internal inline +methods but they are used only in that file. */ + +#ifndef LOCK_MODULE_IMPLEMENTATION +#error Do not include lock0priv.ic outside of the lock/ module +#endif + +/************************************************************************* +Gets the type of a lock. */ +UNIV_INLINE +ulint +lock_get_type( +/*==========*/ + /* out: LOCK_TABLE or LOCK_REC */ + const lock_t* lock) /* in: lock */ +{ + ut_ad(lock); + + return(lock->type_mode & LOCK_TYPE_MASK); +} + +/* vim: set filetype=c: */ diff --git a/storage/innobase/lock/lock0iter.c b/storage/innobase/lock/lock0iter.c new file mode 100644 index 00000000000..cad227e3f8e --- /dev/null +++ b/storage/innobase/lock/lock0iter.c @@ -0,0 +1,91 @@ +/****************************************************** +Lock queue iterator. Can iterate over table and record +lock queues. + +(c) 2007 Innobase Oy + +Created July 16, 2007 Vasil Dimov +*******************************************************/ + +#define LOCK_MODULE_IMPLEMENTATION + +#include "univ.i" +#include "lock0iter.h" +#include "lock0lock.h" +#include "lock0priv.h" +#include "ut0dbg.h" +#include "ut0lst.h" + +/*********************************************************************** +Initialize lock queue iterator so that it starts to iterate from +"lock". bit_no specifies the record number within the heap where the +record is stored. It can be undefined (ULINT_UNDEFINED) in two cases: +1. If the lock is a table lock, thus we have a table lock queue; +2. If the lock is a record lock and it is a wait lock. In this case + bit_no is calculated in this function by using + lock_rec_find_set_bit(). There is exactly one bit set in the bitmap + of a wait lock. */ + +void +lock_queue_iterator_reset( +/*======================*/ + lock_queue_iterator_t* iter, /* out: iterator */ + lock_t* lock, /* in: lock to start from */ + ulint bit_no) /* in: record number in the + heap */ +{ + iter->current_lock = lock; + + if (bit_no != ULINT_UNDEFINED) { + + iter->bit_no = bit_no; + } else { + + switch (lock_get_type(lock)) { + case LOCK_TABLE: + iter->bit_no = ULINT_UNDEFINED; + break; + case LOCK_REC: + iter->bit_no = lock_rec_find_set_bit(lock); + ut_a(iter->bit_no != ULINT_UNDEFINED); + break; + default: + ut_error; + } + } +} + +/*********************************************************************** +Gets the previous lock in the lock queue, returns NULL if there are no +more locks (i.e. the current lock is the first one). The iterator is +receded (if not-NULL is returned). */ + +lock_t* +lock_queue_iterator_get_prev( +/*=========================*/ + /* out: previous lock or NULL */ + lock_queue_iterator_t* iter) /* in/out: iterator */ +{ + ulint bit_no; + lock_t* prev_lock; + + switch (lock_get_type(iter->current_lock)) { + case LOCK_REC: + prev_lock = lock_rec_get_prev( + iter->current_lock, iter->bit_no); + break; + case LOCK_TABLE: + prev_lock = UT_LIST_GET_PREV( + un_member.tab_lock.locks, iter->current_lock); + break; + default: + ut_error; + } + + if (prev_lock != NULL) { + + iter->current_lock = prev_lock; + } + + return(prev_lock); +}