summaryrefslogtreecommitdiff
path: root/innobase/lock
diff options
context:
space:
mode:
authorunknown <monty@mysql.com>2004-05-05 17:05:24 +0300
committerunknown <monty@mysql.com>2004-05-05 17:05:24 +0300
commitcd21f7ce40ac4c7d415544a5b2aa07b1278419ac (patch)
tree3238bd16530e02dbfef96513749a73b7294880f8 /innobase/lock
parent575541b9f755425eaeb07babfa07b6fd30f6d5d1 (diff)
parent7d918f213e64df4af4b00d0798fadf9ed1a872fb (diff)
downloadmariadb-git-cd21f7ce40ac4c7d415544a5b2aa07b1278419ac.tar.gz
Merge with 4.0.19
BitKeeper/etc/logging_ok: auto-union VC++Files/client/mysqlclient.dsp: Auto merged VC++Files/mysql.dsw: Auto merged extra/perror.c: Auto merged extra/replace.c: Auto merged innobase/configure.in: Auto merged innobase/include/lock0lock.h: Auto merged innobase/include/row0mysql.h: Auto merged innobase/include/sync0sync.h: Auto merged innobase/lock/lock0lock.c: Auto merged ltmain.sh: Auto merged BitKeeper/deleted/.del-libmysqld.def~8edf7b8780ce943c: Auto merged innobase/os/os0file.c: Auto merged innobase/pars/lexyy.c: Auto merged innobase/row/row0mysql.c: Auto merged innobase/srv/srv0srv.c: Auto merged innobase/srv/srv0start.c: Auto merged innobase/sync/sync0arr.c: Auto merged innobase/sync/sync0sync.c: Auto merged innobase/trx/trx0trx.c: Auto merged mysql-test/r/alias.result: Auto merged mysql-test/t/system_mysql_db_fix-master.opt: Auto merged mysql-test/r/func_time.result: Automatic merge mysql-test/r/innodb.result: Automatic merge mysql-test/t/alias.test: Automatic merge mysql-test/t/create.test: Automatic merge mysql-test/t/func_time.test: Automatic merge sql/ha_innodb.cc: Automatic merge sql/mysql_priv.h: Automatic merge mysql-test/r/rpl_multi_update.result: Automatic merge mysql-test/t/rpl_error_ignored_table.test: Automatic merge mysql-test/t/rpl_multi_update.test: Automatic merge sql/slave.h: Automatic merge sql/sql_base.cc: Automatic merge sql/sql_db.cc: Automatic merge sql/sql_insert.cc: Automatic merge sql/structs.h: Automatic merge sql/table.cc: Automatic merge strings/longlong2str-x86.s: Automatic merge strings/strings-x86.s: Automatic merge support-files/my-medium.cnf.sh: Automatic merge
Diffstat (limited to 'innobase/lock')
-rw-r--r--innobase/lock/lock0lock.c130
1 files changed, 118 insertions, 12 deletions
diff --git a/innobase/lock/lock0lock.c b/innobase/lock/lock0lock.c
index f12389cb6b2..8805a22bb57 100644
--- a/innobase/lock/lock0lock.c
+++ b/innobase/lock/lock0lock.c
@@ -2001,7 +2001,11 @@ lock_grant(
release it at the end of the SQL statement */
lock->trx->auto_inc_lock = lock;
- }
+ } else if (lock_get_type(lock) == LOCK_TABLE_EXP) {
+ ut_ad(lock_get_mode(lock) == LOCK_S
+ || lock_get_mode(lock) == LOCK_X);
+ lock->trx->n_tables_locked++;
+ }
#ifdef UNIV_DEBUG
if (lock_print_waits) {
@@ -2939,7 +2943,7 @@ retry:
}
if (ret == LOCK_VICTIM_IS_START) {
- if (lock_get_type(lock) == LOCK_TABLE) {
+ if (lock_get_type(lock) & LOCK_TABLE) {
table = lock->un_member.tab_lock.table;
index = NULL;
} else {
@@ -3015,7 +3019,7 @@ lock_deadlock_recursive(
/* Look at the locks ahead of wait_lock in the lock queue */
for (;;) {
- if (lock_get_type(lock) == LOCK_TABLE) {
+ if (lock_get_type(lock) & LOCK_TABLE) {
lock = UT_LIST_GET_PREV(un_member.tab_lock.locks, lock);
} else {
@@ -3347,7 +3351,9 @@ lock_table(
/* out: DB_SUCCESS, DB_LOCK_WAIT,
DB_DEADLOCK, or DB_QUE_THR_SUSPENDED */
ulint flags, /* in: if BTR_NO_LOCKING_FLAG bit is set,
- does nothing */
+ does nothing;
+ if LOCK_TABLE_EXP bits are set,
+ creates an explicit table lock */
dict_table_t* table, /* in: database table in dictionary cache */
ulint mode, /* in: lock mode */
que_thr_t* thr) /* in: query thread */
@@ -3362,6 +3368,8 @@ lock_table(
return(DB_SUCCESS);
}
+ ut_ad(flags == 0 || flags == LOCK_TABLE_EXP);
+
trx = thr_get_trx(thr);
lock_mutex_enter_kernel();
@@ -3390,7 +3398,12 @@ lock_table(
return(err);
}
- lock_table_create(table, mode, trx);
+ lock_table_create(table, mode | flags, trx);
+
+ if (flags) {
+ ut_ad(mode == LOCK_S || mode == LOCK_X);
+ trx->n_tables_locked++;
+ }
lock_mutex_exit_kernel();
@@ -3471,7 +3484,8 @@ lock_table_dequeue(
#ifdef UNIV_SYNC_DEBUG
ut_ad(mutex_own(&kernel_mutex));
#endif /* UNIV_SYNC_DEBUG */
- ut_ad(lock_get_type(in_lock) == LOCK_TABLE);
+ ut_ad(lock_get_type(in_lock) == LOCK_TABLE ||
+ lock_get_type(in_lock) == LOCK_TABLE_EXP);
lock = UT_LIST_GET_NEXT(un_member.tab_lock.locks, in_lock);
@@ -3496,6 +3510,22 @@ lock_table_dequeue(
/*=========================== LOCK RELEASE ==============================*/
/*************************************************************************
+Releases a table lock.
+Releases possible other transactions waiting for this lock. */
+
+void
+lock_table_unlock(
+/*==============*/
+ lock_t* lock) /* in: lock */
+{
+ mutex_enter(&kernel_mutex);
+
+ lock_table_dequeue(lock);
+
+ mutex_exit(&kernel_mutex);
+}
+
+/*************************************************************************
Releases an auto-inc lock a transaction possibly has on a table.
Releases possible other transactions waiting for this lock. */
@@ -3542,7 +3572,7 @@ lock_release_off_kernel(
lock_rec_dequeue_from_page(lock);
} else {
- ut_ad(lock_get_type(lock) == LOCK_TABLE);
+ ut_ad(lock_get_type(lock) & LOCK_TABLE);
if (lock_get_mode(lock) != LOCK_IS
&& 0 != ut_dulint_cmp(trx->undo_no,
@@ -3559,6 +3589,11 @@ lock_release_off_kernel(
}
lock_table_dequeue(lock);
+ if (lock_get_type(lock) == LOCK_TABLE_EXP) {
+ ut_ad(lock_get_mode(lock) == LOCK_S
+ || lock_get_mode(lock) == LOCK_X);
+ trx->n_tables_locked--;
+ }
}
if (count == LOCK_RELEASE_KERNEL_INTERVAL) {
@@ -3578,6 +3613,73 @@ lock_release_off_kernel(
mem_heap_empty(trx->lock_heap);
ut_a(trx->auto_inc_lock == NULL);
+ ut_a(trx->n_tables_locked == 0);
+}
+
+/*************************************************************************
+Releases table locks, and releases possible other transactions waiting
+because of these locks. */
+
+void
+lock_release_tables_off_kernel(
+/*===========================*/
+ trx_t* trx) /* in: transaction */
+{
+ dict_table_t* table;
+ ulint count;
+ lock_t* lock;
+
+#ifdef UNIV_SYNC_DEBUG
+ ut_ad(mutex_own(&kernel_mutex));
+#endif /* UNIV_SYNC_DEBUG */
+
+ lock = UT_LIST_GET_LAST(trx->trx_locks);
+
+ count = 0;
+
+ while (lock != NULL) {
+
+ count++;
+
+ if (lock_get_type(lock) == LOCK_TABLE_EXP) {
+ ut_ad(lock_get_mode(lock) == LOCK_S
+ || lock_get_mode(lock) == LOCK_X);
+ if (trx->insert_undo || trx->update_undo) {
+
+ /* The trx may have modified the table.
+ We block the use of the MySQL query
+ cache for all currently active
+ transactions. */
+
+ table = lock->un_member.tab_lock.table;
+
+ table->query_cache_inv_trx_id =
+ trx_sys->max_trx_id;
+ }
+
+ lock_table_dequeue(lock);
+ trx->n_tables_locked--;
+ lock = UT_LIST_GET_LAST(trx->trx_locks);
+ continue;
+ }
+
+ if (count == LOCK_RELEASE_KERNEL_INTERVAL) {
+ /* Release the kernel mutex for a while, so that we
+ do not monopolize it */
+
+ lock_mutex_exit_kernel();
+
+ lock_mutex_enter_kernel();
+
+ count = 0;
+ }
+
+ lock = UT_LIST_GET_PREV(trx_locks, lock);
+ }
+
+ mem_heap_empty(trx->lock_heap);
+
+ ut_a(trx->n_tables_locked == 0);
}
/*************************************************************************
@@ -3597,7 +3699,7 @@ lock_cancel_waiting_and_release(
lock_rec_dequeue_from_page(lock);
} else {
- ut_ad(lock_get_type(lock) == LOCK_TABLE);
+ ut_ad(lock_get_type(lock) & LOCK_TABLE);
lock_table_dequeue(lock);
}
@@ -3638,7 +3740,7 @@ lock_reset_all_on_table_for_trx(
ut_a(!lock_get_wait(lock));
lock_rec_discard(lock);
- } else if (lock_get_type(lock) == LOCK_TABLE
+ } else if (lock_get_type(lock) & LOCK_TABLE
&& lock->un_member.tab_lock.table == table) {
ut_a(!lock_get_wait(lock));
@@ -3690,8 +3792,12 @@ lock_table_print(
#ifdef UNIV_SYNC_DEBUG
ut_ad(mutex_own(&kernel_mutex));
#endif /* UNIV_SYNC_DEBUG */
- ut_a(lock_get_type(lock) == LOCK_TABLE);
+ ut_a(lock_get_type(lock) == LOCK_TABLE ||
+ lock_get_type(lock) == LOCK_TABLE_EXP);
+ if (lock_get_type(lock) == LOCK_TABLE_EXP) {
+ fputs("EXPLICIT ", file);
+ }
fputs("TABLE LOCK table ", file);
ut_print_name(file, lock->un_member.tab_lock.table->name);
fprintf(file, " trx id %lu %lu",
@@ -4012,7 +4118,7 @@ loop:
lock_rec_print(file, lock);
} else {
- ut_ad(lock_get_type(lock) == LOCK_TABLE);
+ ut_ad(lock_get_type(lock) & LOCK_TABLE);
lock_table_print(file, lock);
}
@@ -4293,7 +4399,7 @@ lock_validate(void)
lock = UT_LIST_GET_FIRST(trx->trx_locks);
while (lock) {
- if (lock_get_type(lock) == LOCK_TABLE) {
+ if (lock_get_type(lock) & LOCK_TABLE) {
lock_table_queue_validate(
lock->un_member.tab_lock.table);