summaryrefslogtreecommitdiff
path: root/storage/innobase/sync
diff options
context:
space:
mode:
authorVasil Dimov <vasil.dimov@oracle.com>2010-04-12 18:20:41 +0300
committerVasil Dimov <vasil.dimov@oracle.com>2010-04-12 18:20:41 +0300
commitc877ff39bceb4df96acf3e54f7c98a2bed12b8ee (patch)
tree04211a3e5734b73e9f94cff511a4a74ff87075f0 /storage/innobase/sync
parentfe0828b3b8193e086abe740572c9b0cb2b7da671 (diff)
parent410e23a6af8b597cdda0890d6ed9008355edee7a (diff)
downloadmariadb-git-c877ff39bceb4df96acf3e54f7c98a2bed12b8ee.tar.gz
Import branches/innodb+ from SVN on top of storage/innobase.
Diffstat (limited to 'storage/innobase/sync')
-rw-r--r--storage/innobase/sync/sync0arr.c8
-rw-r--r--storage/innobase/sync/sync0rw.c21
-rw-r--r--storage/innobase/sync/sync0sync.c114
3 files changed, 121 insertions, 22 deletions
diff --git a/storage/innobase/sync/sync0arr.c b/storage/innobase/sync/sync0arr.c
index ed9e25bf2f2..2cdac11a608 100644
--- a/storage/innobase/sync/sync0arr.c
+++ b/storage/innobase/sync/sync0arr.c
@@ -138,6 +138,11 @@ struct sync_array_struct {
since creation of the array */
};
+#ifdef UNIV_PFS_MUTEX
+/* Key to register the mutex with performance schema */
+UNIV_INTERN mysql_pfs_key_t syn_arr_mutex_key;
+#endif
+
#ifdef UNIV_SYNC_DEBUG
/******************************************************************//**
This function is called only in the debug version. Detects a deadlock
@@ -247,7 +252,8 @@ sync_array_create(
if (protection == SYNC_ARRAY_OS_MUTEX) {
arr->os_mutex = os_mutex_create(NULL);
} else if (protection == SYNC_ARRAY_MUTEX) {
- mutex_create(&arr->mutex, SYNC_NO_ORDER_CHECK);
+ mutex_create(syn_arr_mutex_key,
+ &arr->mutex, SYNC_NO_ORDER_CHECK);
} else {
ut_error;
}
diff --git a/storage/innobase/sync/sync0rw.c b/storage/innobase/sync/sync0rw.c
index d231b6acdf7..c05c823ff61 100644
--- a/storage/innobase/sync/sync0rw.c
+++ b/storage/innobase/sync/sync0rw.c
@@ -168,12 +168,22 @@ UNIV_INTERN ib_int64_t rw_x_exit_count = 0;
UNIV_INTERN rw_lock_list_t rw_lock_list;
UNIV_INTERN mutex_t rw_lock_list_mutex;
+#ifdef UNIV_PFS_MUTEX
+UNIV_INTERN mysql_pfs_key_t rw_lock_list_mutex_key;
+UNIV_INTERN mysql_pfs_key_t rw_lock_mutex_key;
+#endif /* UNIV_PFS_MUTEX */
+
#ifdef UNIV_SYNC_DEBUG
/* The global mutex which protects debug info lists of all rw-locks.
To modify the debug info list of an rw-lock, this mutex has to be
acquired in addition to the mutex protecting the lock. */
UNIV_INTERN mutex_t rw_lock_debug_mutex;
+
+# ifdef UNIV_PFS_MUTEX
+UNIV_INTERN mysql_pfs_key_t rw_lock_debug_mutex_key;
+# endif
+
/* If deadlock detection does not get immediately the mutex,
it may wait for this event */
UNIV_INTERN os_event_t rw_lock_debug_event;
@@ -231,7 +241,7 @@ rw_lock_create_func(
# ifdef UNIV_SYNC_DEBUG
ulint level, /*!< in: level */
# endif /* UNIV_SYNC_DEBUG */
- const char* cmutex_name, /*!< in: mutex name */
+ const char* cmutex_name, /*!< in: mutex name */
#endif /* UNIV_DEBUG */
const char* cfile_name, /*!< in: file name where created */
ulint cline) /*!< in: file line where created */
@@ -240,7 +250,8 @@ rw_lock_create_func(
created, then the following call initializes the sync system. */
#ifndef INNODB_RW_LOCKS_USE_ATOMICS
- mutex_create(rw_lock_get_mutex(lock), SYNC_NO_ORDER_CHECK);
+ mutex_create(rw_lock_mutex_key, rw_lock_get_mutex(lock),
+ SYNC_NO_ORDER_CHECK);
lock->mutex.cfile_name = cfile_name;
lock->mutex.cline = cline;
@@ -298,8 +309,8 @@ the rw-lock is freed. Removes an rw-lock object from the global list. The
rw-lock is checked to be in the non-locked state. */
UNIV_INTERN
void
-rw_lock_free(
-/*=========*/
+rw_lock_free_func(
+/*==============*/
rw_lock_t* lock) /*!< in: rw-lock */
{
ut_ad(rw_lock_validate(lock));
@@ -607,7 +618,7 @@ rw_lock_x_lock_func(
{
ulint index; /*!< index of the reserved wait cell */
ulint i; /*!< spin round count */
- ibool spinning = FALSE;
+ ibool spinning = FALSE;
ut_ad(rw_lock_validate(lock));
diff --git a/storage/innobase/sync/sync0sync.c b/storage/innobase/sync/sync0sync.c
index 569fc6328c4..b9b83adba00 100644
--- a/storage/innobase/sync/sync0sync.c
+++ b/storage/innobase/sync/sync0sync.c
@@ -1,6 +1,6 @@
/*****************************************************************************
-Copyright (c) 1995, 2009, Innobase Oy. All Rights Reserved.
+Copyright (c) 1995, 2010, Innobase Oy. All Rights Reserved.
Copyright (c) 2008, Google Inc.
Portions of this file contain modifications contributed and copyrighted by
@@ -198,6 +198,10 @@ UNIV_INTERN sync_thread_t* sync_thread_level_arrays;
/** Mutex protecting sync_thread_level_arrays */
UNIV_INTERN mutex_t sync_thread_mutex;
+
+# ifdef UNIV_PFS_MUTEX
+UNIV_INTERN mysql_pfs_key_t sync_thread_mutex_key;
+# endif /* UNIV_PFS_MUTEX */
#endif /* UNIV_SYNC_DEBUG */
/** Global list of database mutexes (not OS mutexes) created. */
@@ -206,6 +210,10 @@ UNIV_INTERN ut_list_base_node_t mutex_list;
/** Mutex protecting the mutex_list variable */
UNIV_INTERN mutex_t mutex_list_mutex;
+#ifdef UNIV_PFS_MUTEX
+UNIV_INTERN mysql_pfs_key_t mutex_list_mutex_key;
+#endif /* UNIV_PFS_MUTEX */
+
#ifdef UNIV_SYNC_DEBUG
/** Latching order checks start when this is set TRUE */
UNIV_INTERN ibool sync_order_checks_on = FALSE;
@@ -302,19 +310,29 @@ mutex_create_func(
}
/******************************************************************//**
+NOTE! Use the corresponding macro mutex_free(), not directly this function!
Calling this function is obligatory only if the memory buffer containing
the mutex is freed. Removes a mutex object from the mutex list. The mutex
is checked to be in the reset state. */
UNIV_INTERN
void
-mutex_free(
-/*=======*/
+mutex_free_func(
+/*============*/
mutex_t* mutex) /*!< in: mutex */
{
ut_ad(mutex_validate(mutex));
ut_a(mutex_get_lock_word(mutex) == 0);
ut_a(mutex_get_waiters(mutex) == 0);
+#ifdef UNIV_MEM_DEBUG
+ if (mutex == &mem_hash_mutex) {
+ ut_ad(UT_LIST_GET_LEN(mutex_list) == 1);
+ ut_ad(UT_LIST_GET_FIRST(mutex_list) == &mem_hash_mutex);
+ UT_LIST_REMOVE(list, mutex_list, mutex);
+ goto func_exit;
+ }
+#endif /* UNIV_MEM_DEBUG */
+
if (mutex != &mutex_list_mutex
#ifdef UNIV_SYNC_DEBUG
&& mutex != &sync_thread_mutex
@@ -336,7 +354,9 @@ mutex_free(
}
os_event_free(mutex->event);
-
+#ifdef UNIV_MEM_DEBUG
+func_exit:
+#endif /* UNIV_MEM_DEBUG */
#if !defined(HAVE_ATOMIC_BUILTINS)
os_fast_mutex_free(&(mutex->os_fast_mutex));
#endif
@@ -947,12 +967,62 @@ sync_thread_levels_contain(
}
/******************************************************************//**
+Checks if the level array for the current thread contains a
+mutex or rw-latch at the specified level.
+@return a matching latch, or NULL if not found */
+UNIV_INTERN
+void*
+sync_thread_levels_contains(
+/*========================*/
+ ulint level) /*!< in: latching order level
+ (SYNC_DICT, ...)*/
+{
+ sync_level_t* arr;
+ sync_thread_t* thread_slot;
+ sync_level_t* slot;
+ ulint i;
+
+ if (!sync_order_checks_on) {
+
+ return(NULL);
+ }
+
+ mutex_enter(&sync_thread_mutex);
+
+ thread_slot = sync_thread_level_arrays_find_slot();
+
+ if (thread_slot == NULL) {
+
+ mutex_exit(&sync_thread_mutex);
+
+ return(NULL);
+ }
+
+ arr = thread_slot->levels;
+
+ for (i = 0; i < SYNC_THREAD_N_LEVELS; i++) {
+
+ slot = sync_thread_levels_get_nth(arr, i);
+
+ if (slot->latch != NULL && slot->level == level) {
+
+ mutex_exit(&sync_thread_mutex);
+ return(slot->latch);
+ }
+ }
+
+ mutex_exit(&sync_thread_mutex);
+
+ return(NULL);
+}
+
+/******************************************************************//**
Checks that the level array for the current thread is empty.
-@return TRUE if empty except the exceptions specified below */
+@return a latch, or NULL if empty except the exceptions specified below */
UNIV_INTERN
-ibool
-sync_thread_levels_empty_gen(
-/*=========================*/
+void*
+sync_thread_levels_nonempty_gen(
+/*============================*/
ibool dict_mutex_allowed) /*!< in: TRUE if dictionary mutex is
allowed to be owned by the thread,
also purge_is_running mutex is
@@ -965,7 +1035,7 @@ sync_thread_levels_empty_gen(
if (!sync_order_checks_on) {
- return(TRUE);
+ return(NULL);
}
mutex_enter(&sync_thread_mutex);
@@ -976,7 +1046,7 @@ sync_thread_levels_empty_gen(
mutex_exit(&sync_thread_mutex);
- return(TRUE);
+ return(NULL);
}
arr = thread_slot->levels;
@@ -993,13 +1063,13 @@ sync_thread_levels_empty_gen(
mutex_exit(&sync_thread_mutex);
ut_error;
- return(FALSE);
+ return(slot->latch);
}
}
mutex_exit(&sync_thread_mutex);
- return(TRUE);
+ return(NULL);
}
/******************************************************************//**
@@ -1092,6 +1162,8 @@ sync_thread_add_level(
case SYNC_TRX_SYS_HEADER:
case SYNC_FILE_FORMAT_TAG:
case SYNC_DOUBLEWRITE:
+ case SYNC_BUF_FLUSH_LIST:
+ case SYNC_BUF_FLUSH_ORDER:
case SYNC_BUF_POOL:
case SYNC_SEARCH_SYS:
case SYNC_SEARCH_SYS_CONF:
@@ -1337,18 +1409,22 @@ sync_init(void)
/* Init the mutex list and create the mutex to protect it. */
UT_LIST_INIT(mutex_list);
- mutex_create(&mutex_list_mutex, SYNC_NO_ORDER_CHECK);
+ mutex_create(mutex_list_mutex_key, &mutex_list_mutex,
+ SYNC_NO_ORDER_CHECK);
#ifdef UNIV_SYNC_DEBUG
- mutex_create(&sync_thread_mutex, SYNC_NO_ORDER_CHECK);
+ mutex_create(sync_thread_mutex_key, &sync_thread_mutex,
+ SYNC_NO_ORDER_CHECK);
#endif /* UNIV_SYNC_DEBUG */
/* Init the rw-lock list and create the mutex to protect it. */
UT_LIST_INIT(rw_lock_list);
- mutex_create(&rw_lock_list_mutex, SYNC_NO_ORDER_CHECK);
+ mutex_create(rw_lock_list_mutex_key, &rw_lock_list_mutex,
+ SYNC_NO_ORDER_CHECK);
#ifdef UNIV_SYNC_DEBUG
- mutex_create(&rw_lock_debug_mutex, SYNC_NO_ORDER_CHECK);
+ mutex_create(rw_lock_debug_mutex_key, &rw_lock_debug_mutex,
+ SYNC_NO_ORDER_CHECK);
rw_lock_debug_event = os_event_create(NULL);
rw_lock_debug_waiters = FALSE;
@@ -1370,6 +1446,12 @@ sync_close(void)
mutex = UT_LIST_GET_FIRST(mutex_list);
while (mutex) {
+#ifdef UNIV_MEM_DEBUG
+ if (mutex == &mem_hash_mutex) {
+ mutex = UT_LIST_GET_NEXT(list, mutex);
+ continue;
+ }
+#endif /* UNIV_MEM_DEBUG */
mutex_free(mutex);
mutex = UT_LIST_GET_FIRST(mutex_list);
}