diff options
author | unknown <tsmith@siva.hindu.god> | 2007-01-05 16:05:48 -0700 |
---|---|---|
committer | unknown <tsmith@siva.hindu.god> | 2007-01-05 16:05:48 -0700 |
commit | 0e4155835c637c1c459cc9c77458e88ab4f27545 (patch) | |
tree | 0b356d21101dc7456df092ff091050ef621eefc0 | |
parent | 0275fa0eb235e56af21282d43f2d9ed3bc4eee41 (diff) | |
parent | a5868736ff8c1c314e7c72a2fac9d138b69d56b1 (diff) | |
download | mariadb-git-0e4155835c637c1c459cc9c77458e88ab4f27545.tar.gz |
Merge siva.hindu.god:/home/tsmith/m/inno/jan04/51
into siva.hindu.god:/home/tsmith/m/bk/51-build
storage/innobase/buf/buf0buf.c:
Auto merged
storage/innobase/dict/dict0dict.c:
Auto merged
storage/innobase/ha/ha0ha.c:
Auto merged
storage/innobase/ha/hash0hash.c:
Auto merged
storage/innobase/include/hash0hash.h:
Auto merged
storage/innobase/lock/lock0lock.c:
Auto merged
storage/innobase/log/log0recv.c:
Auto merged
27 files changed, 336 insertions, 268 deletions
diff --git a/storage/innobase/buf/buf0buf.c b/storage/innobase/buf/buf0buf.c index ab0aa1d94d9..ad71b1e5b5c 100644 --- a/storage/innobase/buf/buf0buf.c +++ b/storage/innobase/buf/buf0buf.c @@ -1755,22 +1755,22 @@ buf_page_init_for_read( if (*err == DB_TABLESPACE_DELETED || NULL != buf_page_hash_get(space, offset)) { - /* The page belongs to a space which has been - deleted or is being deleted, or the page is - already in buf_pool, return */ + /* The page belongs to a space which has been + deleted or is being deleted, or the page is + already in buf_pool, return */ mutex_exit(&block->mutex); - mutex_exit(&(buf_pool->mutex)); + mutex_exit(&(buf_pool->mutex)); - buf_block_free(block); + buf_block_free(block); - if (mode == BUF_READ_IBUF_PAGES_ONLY) { + if (mode == BUF_READ_IBUF_PAGES_ONLY) { - mtr_commit(&mtr); - } + mtr_commit(&mtr); + } - return(NULL); - } + return(NULL); + } ut_ad(block); diff --git a/storage/innobase/buf/buf0flu.c b/storage/innobase/buf/buf0flu.c index 49b81196a64..64060dab8ae 100644 --- a/storage/innobase/buf/buf0flu.c +++ b/storage/innobase/buf/buf0flu.c @@ -854,8 +854,10 @@ buf_flush_batch( ut_ad((flush_type == BUF_FLUSH_LRU) || (flush_type == BUF_FLUSH_LIST)); +#ifdef UNIV_SYNC_DEBUG ut_ad((flush_type != BUF_FLUSH_LIST) || sync_thread_levels_empty_gen(TRUE)); +#endif /* UNIV_SYNC_DEBUG */ mutex_enter(&(buf_pool->mutex)); if ((buf_pool->n_flush[flush_type] > 0) diff --git a/storage/innobase/dict/dict0dict.c b/storage/innobase/dict/dict0dict.c index 323771c6455..3d1fd1daf28 100644 --- a/storage/innobase/dict/dict0dict.c +++ b/storage/innobase/dict/dict0dict.c @@ -801,43 +801,20 @@ dict_init(void) } /************************************************************************** -Returns a table object. NOTE! This is a high-level function to be used -mainly from outside the 'dict' directory. Inside this directory -dict_table_get_low is usually the appropriate function. */ +Returns a table object and optionally increment its MySQL open handle count. +NOTE! This is a high-level function to be used mainly from outside the +'dict' directory. Inside this directory dict_table_get_low is usually the +appropriate function. */ dict_table_t* dict_table_get( /*===========*/ /* out: table, NULL if does not exist */ - const char* table_name) /* in: table name */ -{ - dict_table_t* table; - - mutex_enter(&(dict_sys->mutex)); - - table = dict_table_get_low(table_name); - - mutex_exit(&(dict_sys->mutex)); - - if (table != NULL) { - if (!table->stat_initialized) { - dict_update_statistics(table); - } - } - - return(table); -} - -/************************************************************************** -Returns a table object and increments MySQL open handle count on the table. */ - -dict_table_t* -dict_table_get_and_increment_handle_count( -/*======================================*/ - /* out: table, NULL if - does not exist */ - const char* table_name) /* in: table name */ + const char* table_name, /* in: table name */ + ibool inc_mysql_count) + /* in: whether to increment the open + handle count on the table */ { dict_table_t* table; @@ -845,15 +822,17 @@ dict_table_get_and_increment_handle_count( table = dict_table_get_low(table_name); - if (table != NULL) { - + if (inc_mysql_count && table) { table->n_mysql_handles_opened++; } mutex_exit(&(dict_sys->mutex)); if (table != NULL) { - if (!table->stat_initialized && !table->ibd_file_missing) { + if (!table->stat_initialized) { + /* If table->ibd_file_missing == TRUE, this will + print an error message and return without doing + anything. */ dict_update_statistics(table); } } diff --git a/storage/innobase/ha/ha0ha.c b/storage/innobase/ha/ha0ha.c index aa2f86d2869..644dcd962ff 100644 --- a/storage/innobase/ha/ha0ha.c +++ b/storage/innobase/ha/ha0ha.c @@ -18,16 +18,18 @@ Creates a hash table with >= n array cells. The actual number of cells is chosen to be a prime number slightly bigger than n. */ hash_table_t* -ha_create( -/*======*/ +ha_create_func( +/*===========*/ /* out, own: created table */ ibool in_btr_search, /* in: TRUE if the hash table is used in the btr_search module */ ulint n, /* in: number of array cells */ - ulint n_mutexes, /* in: number of mutexes to protect the - hash table: must be a power of 2, or 0 */ - ulint mutex_level) /* in: level of the mutexes in the latching +#ifdef UNIV_SYNC_DEBUG + ulint mutex_level, /* in: level of the mutexes in the latching order: this is used in the debug version */ +#endif /* UNIV_SYNC_DEBUG */ + ulint n_mutexes) /* in: number of mutexes to protect the + hash table: must be a power of 2, or 0 */ { hash_table_t* table; ulint i; diff --git a/storage/innobase/ha/hash0hash.c b/storage/innobase/ha/hash0hash.c index 1e5078d1d92..8b467966ae5 100644 --- a/storage/innobase/ha/hash0hash.c +++ b/storage/innobase/ha/hash0hash.c @@ -129,13 +129,15 @@ hash_table_free( Creates a mutex array to protect a hash table. */ void -hash_create_mutexes( -/*================*/ +hash_create_mutexes_func( +/*=====================*/ hash_table_t* table, /* in: hash table */ - ulint n_mutexes, /* in: number of mutexes, must be a - power of 2 */ - ulint sync_level) /* in: latching order level of the +#ifdef UNIV_SYNC_DEBUG + ulint sync_level, /* in: latching order level of the mutexes: used in the debug version */ +#endif /* UNIV_SYNC_DEBUG */ + ulint n_mutexes) /* in: number of mutexes, must be a + power of 2 */ { ulint i; diff --git a/storage/innobase/handler/ha_innodb.cc b/storage/innobase/handler/ha_innodb.cc index 4d835b41863..90d1701a565 100644 --- a/storage/innobase/handler/ha_innodb.cc +++ b/storage/innobase/handler/ha_innodb.cc @@ -39,9 +39,6 @@ have disables the InnoDB inlining in this file. */ #include <myisampack.h> #include <mysys_err.h> #include <my_sys.h> - -#define MAX_ULONG_BIT ((ulong) 1 << (sizeof(ulong)*8-1)) - #include "ha_innodb.h" pthread_mutex_t innobase_share_mutex, /* to protect innobase_open_files */ @@ -1261,18 +1258,6 @@ trx_is_interrupted( return(trx && trx->mysql_thd && ((THD*) trx->mysql_thd)->killed); } -/************************************************************************** -Obtain a pointer to the MySQL THD object, as in current_thd(). This -definition must match the one in sql/ha_innodb.cc! */ -extern "C" -void* -innobase_current_thd(void) -/*======================*/ - /* out: MySQL THD object */ -{ - return(current_thd); -} - /********************************************************************* Call this when you have opened a new table handle in HANDLER, before you call index_read_idx() etc. Actually, we can let the cursor stay open even @@ -2354,7 +2339,7 @@ ha_innobase::open( /* Get pointer to a table object in InnoDB dictionary cache */ - ib_table = dict_table_get_and_increment_handle_count(norm_name); + ib_table = dict_table_get(norm_name, TRUE); if (NULL == ib_table) { ut_print_timestamp(stderr); @@ -4451,7 +4436,7 @@ ha_innobase::rnd_pos( } if (error) { - DBUG_PRINT("error", ("Got error: %d", error)); + DBUG_PRINT("error", ("Got error: %d", error)); DBUG_RETURN(error); } @@ -4932,7 +4917,7 @@ ha_innobase::create( log_buffer_flush_to_disk(); - innobase_table = dict_table_get(norm_name); + innobase_table = dict_table_get(norm_name, FALSE); DBUG_ASSERT(innobase_table != 0); @@ -5543,16 +5528,10 @@ ha_innobase::info( prebuilt->trx->op_info = (char*) "returning various info to MySQL"; - if (ib_table->space != 0) { - my_snprintf(path, sizeof(path), "%s/%s%s", - mysql_data_home, ib_table->name, ".ibd"); - unpack_filename(path,path); - } else { - my_snprintf(path, sizeof(path), "%s/%s%s", + my_snprintf(path, sizeof(path), "%s/%s%s", mysql_data_home, ib_table->name, reg_ext); - unpack_filename(path,path); - } + unpack_filename(path,path); /* Note that we do not know the access time of the table, nor the CHECK TABLE time, nor the UPDATE or INSERT time. */ @@ -6605,22 +6584,23 @@ innodb_mutex_show_status( { char buf1[IO_SIZE], buf2[IO_SIZE]; mutex_t* mutex; +#ifdef UNIV_DEBUG ulint rw_lock_count= 0; ulint rw_lock_count_spin_loop= 0; ulint rw_lock_count_spin_rounds= 0; ulint rw_lock_count_os_wait= 0; ulint rw_lock_count_os_yield= 0; ulonglong rw_lock_wait_time= 0; +#endif /* UNIV_DEBUG */ uint hton_name_len= strlen(innobase_hton_name), buf1len, buf2len; DBUG_ENTER("innodb_mutex_show_status"); -#ifdef MUTEX_PROTECT_TO_BE_ADDED_LATER - mutex_enter(&mutex_list_mutex); -#endif + mutex_enter_noninline(&mutex_list_mutex); mutex = UT_LIST_GET_FIRST(mutex_list); while (mutex != NULL) { +#ifdef UNIV_DEBUG if (mutex->mutex_type != 1) { if (mutex->count_using > 0) { buf1len= my_snprintf(buf1, sizeof(buf1), @@ -6636,14 +6616,13 @@ innodb_mutex_show_status( mutex->count_spin_rounds, mutex->count_os_wait, mutex->count_os_yield, - (ulong) (mutex->lspent_time/1000)); + (ulong) (mutex->lspent_time/1000)); if (stat_print(thd, innobase_hton_name, hton_name_len, buf1, buf1len, buf2, buf2len)) { -#ifdef MUTEX_PROTECT_TO_BE_ADDED_LATER - mutex_exit(&mutex_list_mutex); -#endif + mutex_exit_noninline( + &mutex_list_mutex); DBUG_RETURN(1); } } @@ -6656,26 +6635,39 @@ innodb_mutex_show_status( rw_lock_count_os_yield += mutex->count_os_yield; rw_lock_wait_time += mutex->lspent_time; } +#else /* UNIV_DEBUG */ + buf1len= my_snprintf(buf1, sizeof(buf1), "%s:%lu", + mutex->cfile_name, (ulong) mutex->cline); + buf2len= my_snprintf(buf2, sizeof(buf2), "os_waits=%lu", + mutex->count_os_wait); + + if (stat_print(thd, innobase_hton_name, + hton_name_len, buf1, buf1len, + buf2, buf2len)) { + mutex_exit_noninline(&mutex_list_mutex); + DBUG_RETURN(1); + } +#endif /* UNIV_DEBUG */ mutex = UT_LIST_GET_NEXT(list, mutex); } + mutex_exit_noninline(&mutex_list_mutex); + +#ifdef UNIV_DEBUG buf2len= my_snprintf(buf2, sizeof(buf2), "count=%lu, spin_waits=%lu, spin_rounds=%lu, " "os_waits=%lu, os_yields=%lu, os_wait_times=%lu", rw_lock_count, rw_lock_count_spin_loop, rw_lock_count_spin_rounds, rw_lock_count_os_wait, rw_lock_count_os_yield, - (ulong) (rw_lock_wait_time/1000)); + (ulong) (rw_lock_wait_time/1000)); if (stat_print(thd, innobase_hton_name, hton_name_len, STRING_WITH_LEN("rw_lock_mutexes"), buf2, buf2len)) { DBUG_RETURN(1); } - -#ifdef MUTEX_PROTECT_TO_BE_ADDED_LATER - mutex_exit(&mutex_list_mutex); -#endif +#endif /* UNIV_DEBUG */ DBUG_RETURN(FALSE); } @@ -7348,7 +7340,6 @@ innobase_get_at_most_n_mbchars( } } -extern "C" { /********************************************************************** This function returns true if @@ -7358,33 +7349,34 @@ is either REPLACE or LOAD DATA INFILE REPLACE. 2) SQL-query in the current thread is INSERT ON DUPLICATE KEY UPDATE. -NOTE that /mysql/innobase/row/row0ins.c must contain the +NOTE that storage/innobase/row/row0ins.c must contain the prototype for this function ! */ - +extern "C" ibool innobase_query_is_update(void) /*==========================*/ { - THD* thd; + THD* thd = current_thd; - thd = (THD *)innobase_current_thd(); + if (!thd) { + /* InnoDB's internal threads may run InnoDB stored procedures + that call this function. Then current_thd is not defined + (it is probably NULL). */ - if (thd->lex->sql_command == SQLCOM_REPLACE || - thd->lex->sql_command == SQLCOM_REPLACE_SELECT || - (thd->lex->sql_command == SQLCOM_LOAD && - thd->lex->duplicates == DUP_REPLACE)) { - - return(1); + return(FALSE); } - if (thd->lex->sql_command == SQLCOM_INSERT && - thd->lex->duplicates == DUP_UPDATE) { - - return(1); + switch (thd->lex->sql_command) { + case SQLCOM_REPLACE: + case SQLCOM_REPLACE_SELECT: + return(TRUE); + case SQLCOM_LOAD: + return(thd->lex->duplicates == DUP_REPLACE); + case SQLCOM_INSERT: + return(thd->lex->duplicates == DUP_UPDATE); + default: + return(FALSE); } - - return(0); -} } /*********************************************************************** diff --git a/storage/innobase/include/btr0sea.h b/storage/innobase/include/btr0sea.h index 8b4408ef852..281587ad060 100644 --- a/storage/innobase/include/btr0sea.h +++ b/storage/innobase/include/btr0sea.h @@ -160,7 +160,7 @@ struct btr_search_struct{ number of full fields */ ulint n_bytes; /* recommended prefix: number of bytes in an incomplete field; - cf. BTR_PAGE_MAX_REC_SIZE */ + see also BTR_PAGE_MAX_REC_SIZE */ ibool left_side; /* TRUE or FALSE, depending on whether the leftmost record of several records with the same prefix should be indexed in the diff --git a/storage/innobase/include/buf0buf.ic b/storage/innobase/include/buf0buf.ic index 43895295734..c448c28933a 100644 --- a/storage/innobase/include/buf0buf.ic +++ b/storage/innobase/include/buf0buf.ic @@ -625,8 +625,6 @@ buf_page_release( RW_NO_LATCH */ mtr_t* mtr) /* in: mtr */ { - ulint buf_fix_count; - ut_ad(block); ut_a(block->state == BUF_BLOCK_FILE_PAGE); @@ -643,8 +641,7 @@ buf_page_release( #ifdef UNIV_SYNC_DEBUG rw_lock_s_unlock(&(block->debug_latch)); #endif - buf_fix_count = block->buf_fix_count; - block->buf_fix_count = buf_fix_count - 1; + block->buf_fix_count--; mutex_exit(&block->mutex); diff --git a/storage/innobase/include/data0type.ic b/storage/innobase/include/data0type.ic index b447c9c39c2..b8c24bb074a 100644 --- a/storage/innobase/include/data0type.ic +++ b/storage/innobase/include/data0type.ic @@ -65,8 +65,8 @@ dtype_get_mblen( innobase_get_cset_width(dtype_get_charset_coll(prtype), mbminlen, mbmaxlen); ut_ad(*mbminlen <= *mbmaxlen); - ut_ad(*mbminlen <= 2); /* cf. the bit-field in dtype_t */ - ut_ad(*mbmaxlen < 1 << 3); /* cf. the bit-field in dtype_t */ + ut_ad(*mbminlen <= 2); /* mbminlen in dtype_t is 0..3 */ + ut_ad(*mbmaxlen < 1 << 3); /* mbmaxlen in dtype_t is 0..7 */ #else /* !UNIV_HOTBACKUP */ ut_a(mtype <= DATA_BINARY); *mbminlen = *mbmaxlen = 1; diff --git a/storage/innobase/include/dict0dict.h b/storage/innobase/include/dict0dict.h index 2582effbb29..836a6290498 100644 --- a/storage/innobase/include/dict0dict.h +++ b/storage/innobase/include/dict0dict.h @@ -326,26 +326,20 @@ dict_foreign_parse_drop_constraints( const char*** constraints_to_drop); /* out: id's of the constraints to drop */ /************************************************************************** -Returns a table object. NOTE! This is a high-level function to be used -mainly from outside the 'dict' directory. Inside this directory -dict_table_get_low is usually the appropriate function. */ +Returns a table object and optionally increment its MySQL open handle count. +NOTE! This is a high-level function to be used mainly from outside the +'dict' directory. Inside this directory dict_table_get_low is usually the +appropriate function. */ dict_table_t* dict_table_get( /*===========*/ /* out: table, NULL if does not exist */ - const char* table_name); /* in: table name */ -/************************************************************************** -Returns a table object and increments MySQL open handle count on the table. -*/ - -dict_table_t* -dict_table_get_and_increment_handle_count( -/*======================================*/ - /* out: table, NULL if - does not exist */ - const char* table_name); /* in: table name */ + const char* table_name, /* in: table name */ + ibool inc_mysql_count); + /* in: whether to increment the open + handle count on the table */ /************************************************************************** Returns a table object based on table id. */ diff --git a/storage/innobase/include/ha0ha.h b/storage/innobase/include/ha0ha.h index 9fc80ed301c..beaa06ae755 100644 --- a/storage/innobase/include/ha0ha.h +++ b/storage/innobase/include/ha0ha.h @@ -41,16 +41,23 @@ Creates a hash table with >= n array cells. The actual number of cells is chosen to be a prime number slightly bigger than n. */ hash_table_t* -ha_create( -/*======*/ +ha_create_func( +/*===========*/ /* out, own: created table */ ibool in_btr_search, /* in: TRUE if the hash table is used in the btr_search module */ ulint n, /* in: number of array cells */ - ulint n_mutexes, /* in: number of mutexes to protect the - hash table: must be a power of 2 */ - ulint mutex_level); /* in: level of the mutexes in the latching +#ifdef UNIV_SYNC_DEBUG + ulint mutex_level, /* in: level of the mutexes in the latching order: this is used in the debug version */ +#endif /* UNIV_SYNC_DEBUG */ + ulint n_mutexes); /* in: number of mutexes to protect the + hash table: must be a power of 2 */ +#ifdef UNIV_SYNC_DEBUG +# define ha_create(b,n_c,n_m,level) ha_create_func(b,n_c,level,n_m) +#else /* UNIV_SYNC_DEBUG */ +# define ha_create(b,n_c,n_m,level) ha_create_func(b,n_c,n_m) +#endif /* UNIV_SYNC_DEBUG */ /***************************************************************** Inserts an entry into a hash table. If an entry with the same fold number is found, its node is updated to point to the new data, and no new node diff --git a/storage/innobase/include/hash0hash.h b/storage/innobase/include/hash0hash.h index 3685dbb1d82..efd9bcb4c54 100644 --- a/storage/innobase/include/hash0hash.h +++ b/storage/innobase/include/hash0hash.h @@ -31,12 +31,20 @@ hash0_create( Creates a mutex array to protect a hash table. */ void -hash_create_mutexes( -/*================*/ +hash_create_mutexes_func( +/*=====================*/ hash_table_t* table, /* in: hash table */ - ulint n_mutexes, /* in: number of mutexes */ - ulint sync_level); /* in: latching order level of the +#ifdef UNIV_SYNC_DEBUG + ulint sync_level, /* in: latching order level of the mutexes: used in the debug version */ +#endif /* UNIV_SYNC_DEBUG */ + ulint n_mutexes); /* in: number of mutexes */ +#ifdef UNIV_SYNC_DEBUG +# define hash_create_mutexes(t,n,level) hash_create_mutexes_func(t,level,n) +#else /* UNIV_SYNC_DEBUG */ +# define hash_create_mutexes(t,n,level) hash_create_mutexes_func(t,n) +#endif /* UNIV_SYNC_DEBUG */ + /***************************************************************** Frees a hash table. */ diff --git a/storage/innobase/include/sync0rw.h b/storage/innobase/include/sync0rw.h index 7c0241f2e02..abf04253141 100644 --- a/storage/innobase/include/sync0rw.h +++ b/storage/innobase/include/sync0rw.h @@ -61,8 +61,18 @@ Creates, or rather, initializes an rw-lock object in a specified memory location (which must be appropriately aligned). The rw-lock is initialized to the non-locked state. Explicit freeing of the rw-lock with rw_lock_free is necessary only if the memory block containing it is freed. */ -#define rw_lock_create(L, level) \ - rw_lock_create_func((L), (level), __FILE__, __LINE__, #L) +#ifdef UNIV_DEBUG +# ifdef UNIV_SYNC_DEBUG +# define rw_lock_create(L, level) \ + rw_lock_create_func((L), (level), #L, __FILE__, __LINE__) +# else /* UNIV_SYNC_DEBUG */ +# define rw_lock_create(L, level) \ + rw_lock_create_func((L), #L, __FILE__, __LINE__) +# endif /* UNIV_SYNC_DEBUG */ +#else /* UNIV_DEBUG */ +# define rw_lock_create(L, level) \ + rw_lock_create_func((L), __FILE__, __LINE__) +#endif /* UNIV_DEBUG */ /********************************************************************** Creates, or rather, initializes an rw-lock object in a specified memory @@ -74,10 +84,14 @@ void rw_lock_create_func( /*================*/ rw_lock_t* lock, /* in: pointer to memory */ +#ifdef UNIV_DEBUG +# ifdef UNIV_SYNC_DEBUG ulint level, /* in: level */ +# endif /* UNIV_SYNC_DEBUG */ + 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 */ - const char* cmutex_name); /* in: mutex name */ + ulint cline); /* in: file line where created */ /********************************************************************** Calling this function is obligatory only if the memory buffer containing the rw-lock is freed. Removes an rw-lock object from the global list. The diff --git a/storage/innobase/include/sync0sync.h b/storage/innobase/include/sync0sync.h index a1184d44257..e7e135c0c7e 100644 --- a/storage/innobase/include/sync0sync.h +++ b/storage/innobase/include/sync0sync.h @@ -39,8 +39,18 @@ location (which must be appropriately aligned). The mutex is initialized in the reset state. Explicit freeing of the mutex with mutex_free is necessary only if the memory block containing it is freed. */ -#define mutex_create(M, level) \ - mutex_create_func((M), (level), __FILE__, __LINE__, #M) +#ifdef UNIV_DEBUG +# ifdef UNIV_SYNC_DEBUG +# define mutex_create(M, level) \ + mutex_create_func((M), #M, (level), __FILE__, __LINE__) +# else +# define mutex_create(M, level) \ + mutex_create_func((M), #M, __FILE__, __LINE__) +# endif +#else +# define mutex_create(M, level) \ + mutex_create_func((M), __FILE__, __LINE__) +#endif /********************************************************************** Creates, or rather, initializes a mutex object in a specified memory @@ -52,10 +62,14 @@ void mutex_create_func( /*==============*/ mutex_t* mutex, /* in: pointer to memory */ +#ifdef UNIV_DEBUG + const char* cmutex_name, /* in: mutex name */ +# ifdef UNIV_SYNC_DEBUG ulint level, /* in: level */ +# endif /* UNIV_SYNC_DEBUG */ +#endif /* UNIV_DEBUG */ const char* cfile_name, /* in: file name where created */ - ulint cline, /* in: file line where created */ - const char* cmutex_name); /* in: mutex name */ + ulint cline); /* in: file line where created */ /********************************************************************** 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 @@ -149,6 +163,7 @@ void sync_print( /*=======*/ FILE* file); /* in: file where to print */ +#ifdef UNIV_DEBUG /********************************************************************** Checks that the mutex has been initialized. */ @@ -156,6 +171,8 @@ ibool mutex_validate( /*===========*/ mutex_t* mutex); +#endif /* UNIV_DEBUG */ +#ifdef UNIV_SYNC_DEBUG /********************************************************************** Adds a latch and its level in the thread level array. Allocates the memory for the array if called first time for this OS thread. Makes the checks @@ -197,7 +214,6 @@ sync_thread_levels_empty_gen( allowed to be owned by the thread, also purge_is_running mutex is allowed */ -#ifdef UNIV_SYNC_DEBUG /********************************************************************** Checks that the current thread owns the mutex. Works only in the debug version. */ @@ -465,26 +481,29 @@ struct mutex_struct { ulint line; /* Line where the mutex was locked */ os_thread_id_t thread_id; /* Debug version: The thread id of the thread which locked the mutex. */ -#endif /* UNIV_SYNC_DEBUG */ ulint level; /* Level in the global latching order */ +#endif /* UNIV_SYNC_DEBUG */ const char* cfile_name;/* File name where mutex created */ - ulint cline; /* Line where created */ - ulint magic_n; + ulint cline; /* Line where created */ +#ifdef UNIV_DEBUG + ulint magic_n; +# define MUTEX_MAGIC_N (ulint)979585 +#endif /* UNIV_DEBUG */ #ifndef UNIV_HOTBACKUP - ulong count_using; /* count of times mutex used */ - ulong count_spin_loop; /* count of spin loops */ - ulong count_spin_rounds; /* count of spin rounds */ - ulong count_os_wait; /* count of os_wait */ - ulong count_os_yield; /* count of os_wait */ - ulonglong lspent_time; /* mutex os_wait timer msec */ - ulonglong lmax_spent_time; /* mutex os_wait timer msec */ - const char* cmutex_name;/* mutex name */ - ulint mutex_type;/* 0 - usual mutex 1 - rw_lock mutex */ + ulong count_os_wait; /* count of os_wait */ +# ifdef UNIV_DEBUG + ulong count_using; /* count of times mutex used */ + ulong count_spin_loop; /* count of spin loops */ + ulong count_spin_rounds; /* count of spin rounds */ + ulong count_os_yield; /* count of os_wait */ + ulonglong lspent_time; /* mutex os_wait timer msec */ + ulonglong lmax_spent_time; /* mutex os_wait timer msec */ + const char* cmutex_name;/* mutex name */ + ulint mutex_type;/* 0 - usual mutex 1 - rw_lock mutex */ +# endif /* UNIV_DEBUG */ #endif /* !UNIV_HOTBACKUP */ }; -#define MUTEX_MAGIC_N (ulint)979585 - /* The global array of wait cells for implementation of the databases own mutexes and read-write locks. Appears here for debugging purposes only! */ @@ -496,20 +515,16 @@ to 20 microseconds. */ #define SYNC_SPIN_ROUNDS srv_n_spin_wait_rounds -#define SYNC_INFINITE_TIME ((ulint)(-1)) - -/* Means that a timeout elapsed when waiting */ - -#define SYNC_TIME_EXCEEDED (ulint)1 - /* The number of system calls made in this module. Intended for performance monitoring. */ extern ulint mutex_system_call_count; extern ulint mutex_exit_count; +#ifdef UNIV_SYNC_DEBUG /* Latching order checks start when this is set TRUE */ extern ibool sync_order_checks_on; +#endif /* UNIV_SYNC_DEBUG */ /* This variable is set to TRUE when sync_init is called */ extern ibool sync_initialized; diff --git a/storage/innobase/include/sync0sync.ic b/storage/innobase/include/sync0sync.ic index bcecc3478b3..4b48a1469ff 100644 --- a/storage/innobase/include/sync0sync.ic +++ b/storage/innobase/include/sync0sync.ic @@ -254,9 +254,9 @@ mutex_enter_func( /* Note that we do not peek at the value of lock_word before trying the atomic test_and_set; we could peek, and possibly save time. */ -#ifndef UNIV_HOTBACKUP +#if defined UNIV_DEBUG && !defined UNIV_HOTBACKUP mutex->count_using++; -#endif /* UNIV_HOTBACKUP */ +#endif /* UNIV_DEBUG && !UNIV_HOTBACKUP */ if (!mutex_test_and_set(mutex)) { #ifdef UNIV_SYNC_DEBUG diff --git a/storage/innobase/include/univ.i b/storage/innobase/include/univ.i index f471fe136b0..7a5cb21f07a 100644 --- a/storage/innobase/include/univ.i +++ b/storage/innobase/include/univ.i @@ -83,19 +83,27 @@ memory is read outside the allocated blocks. */ /* Make a non-inline debug version */ #if 0 -#define UNIV_DEBUG -#define UNIV_MEM_DEBUG -#define UNIV_IBUF_DEBUG -#define UNIV_SYNC_DEBUG -#define UNIV_SEARCH_DEBUG -#define UNIV_SYNC_PERF_STAT -#define UNIV_SEARCH_PERF_STAT -#define UNIV_SRV_PRINT_LATCH_WAITS -#define UNIV_BTR_PRINT +#define UNIV_DEBUG /* Enable ut_ad() assertions */ +#define UNIV_LIST_DEBUG /* debug UT_LIST_ macros */ +#define UNIV_MEM_DEBUG /* detect memory leaks etc */ +#define UNIV_IBUF_DEBUG /* debug the insert buffer; +this limits the database to IBUF_COUNT_N_SPACES and IBUF_COUNT_N_PAGES, +and the insert buffer must be empty when the database is started */ +#define UNIV_SYNC_DEBUG /* debug mutex and latch +operations (very slow); also UNIV_DEBUG must be defined */ +#define UNIV_SEARCH_DEBUG /* debug B-tree comparisons */ +#define UNIV_SYNC_PERF_STAT /* operation counts for + rw-locks and mutexes */ +#define UNIV_SEARCH_PERF_STAT /* statistics for the + adaptive hash index */ +#define UNIV_SRV_PRINT_LATCH_WAITS /* enable diagnostic output + in sync0sync.c */ +#define UNIV_BTR_PRINT /* enable functions for + printing B-trees */ #endif -#define UNIV_BTR_DEBUG -#define UNIV_LIGHT_MEM_DEBUG +#define UNIV_BTR_DEBUG /* check B-tree links */ +#define UNIV_LIGHT_MEM_DEBUG /* light memory debugging */ #ifdef HAVE_purify /* The following sets all new allocated memory to zero before use: diff --git a/storage/innobase/include/ut0lst.h b/storage/innobase/include/ut0lst.h index d19885d6edc..9735bf315c6 100644 --- a/storage/innobase/include/ut0lst.h +++ b/storage/innobase/include/ut0lst.h @@ -124,7 +124,7 @@ name, NODE1 and NODE2 are pointers to nodes. */ }\ /* Invalidate the pointers in a list node. */ -#ifdef UNIV_DEBUG +#ifdef UNIV_LIST_DEBUG # define UT_LIST_REMOVE_CLEAR(NAME, N) \ ((N)->NAME.prev = (N)->NAME.next = (void*) -1) #else diff --git a/storage/innobase/lock/lock0lock.c b/storage/innobase/lock/lock0lock.c index d0111d10960..e7dcb86948a 100644 --- a/storage/innobase/lock/lock0lock.c +++ b/storage/innobase/lock/lock0lock.c @@ -4391,10 +4391,6 @@ loop: trx->read_view->up_limit_id)); } - fprintf(file, - "Trx has approximately %lu row locks\n", - (ulong) lock_number_of_rows_locked(trx)); - if (trx->que_state == TRX_QUE_LOCK_WAIT) { fprintf(file, "------- TRX HAS BEEN WAITING %lu SEC" diff --git a/storage/innobase/log/log0recv.c b/storage/innobase/log/log0recv.c index c12998f3b7c..b6a8a443217 100644 --- a/storage/innobase/log/log0recv.c +++ b/storage/innobase/log/log0recv.c @@ -33,6 +33,7 @@ Created 9/20/1997 Heikki Tuuri #include "btr0cur.h" #include "dict0boot.h" #include "fil0fil.h" +#include "sync0sync.h" #ifdef UNIV_HOTBACKUP /* This is set to FALSE if the backup was originally taken with the @@ -190,6 +191,7 @@ recv_sys_empty_hash(void) recv_sys->addr_hash = hash0_create(buf_pool_get_curr_size() / 256); } +#ifndef UNIV_LOG_DEBUG /************************************************************ Frees the recovery system. */ static @@ -209,6 +211,7 @@ recv_sys_free(void) mutex_exit(&(recv_sys->mutex)); } +#endif /* UNIV_LOG_DEBUG */ /************************************************************ Truncates possible corrupted or extra records from a log group. */ @@ -2855,6 +2858,15 @@ recv_recovery_from_checkpoint_finish(void) #ifndef UNIV_LOG_DEBUG recv_sys_free(); #endif + +#ifdef UNIV_SYNC_DEBUG + /* Wait for a while so that created threads have time to suspend + themselves before we switch the latching order checks on */ + os_thread_sleep(1000000); + + /* Switch latching order checks on in sync0sync.c */ + sync_order_checks_on = TRUE; +#endif if (srv_force_recovery < SRV_FORCE_NO_TRX_UNDO) { /* Rollback the uncommitted transactions which have no user session */ diff --git a/storage/innobase/row/row0ins.c b/storage/innobase/row/row0ins.c index aeaa83daa4d..1fba0abcdaf 100644 --- a/storage/innobase/row/row0ins.c +++ b/storage/innobase/row/row0ins.c @@ -1524,7 +1524,8 @@ row_ins_check_foreign_constraints( if (foreign->foreign_index == index) { if (foreign->referenced_table == NULL) { - dict_table_get(foreign->referenced_table_name); + dict_table_get(foreign->referenced_table_name, + FALSE); } if (0 == trx->dict_operation_lock_mode) { diff --git a/storage/innobase/row/row0sel.c b/storage/innobase/row/row0sel.c index c6b117cdafa..bee9f1472ce 100644 --- a/storage/innobase/row/row0sel.c +++ b/storage/innobase/row/row0sel.c @@ -1831,7 +1831,9 @@ stop_for_a_while: mtr_commit(&mtr); +#ifdef UNIV_SYNC_DEBUG ut_ad(sync_thread_levels_empty_gen(TRUE)); +#endif /* UNIV_SYNC_DEBUG */ err = DB_SUCCESS; goto func_exit; @@ -1850,7 +1852,9 @@ commit_mtr_for_a_while: leaf_contains_updates = FALSE; mtr_has_extra_clust_latch = FALSE; +#ifdef UNIV_SYNC_DEBUG ut_ad(sync_thread_levels_empty_gen(TRUE)); +#endif /* UNIV_SYNC_DEBUG */ goto table_loop; @@ -1866,7 +1870,9 @@ lock_wait_or_error: mtr_commit(&mtr); +#ifdef UNIV_SYNC_DEBUG ut_ad(sync_thread_levels_empty_gen(TRUE)); +#endif /* UNIV_SYNC_DEBUG */ func_exit: if (UNIV_LIKELY_NULL(heap)) { @@ -4447,7 +4453,7 @@ row_search_check_if_query_cache_permitted( dict_table_t* table; ibool ret = FALSE; - table = dict_table_get(norm_name); + table = dict_table_get(norm_name, FALSE); if (table == NULL) { diff --git a/storage/innobase/row/row0upd.c b/storage/innobase/row/row0upd.c index 6533ac93d7d..c91cc449b96 100644 --- a/storage/innobase/row/row0upd.c +++ b/storage/innobase/row/row0upd.c @@ -202,7 +202,8 @@ row_upd_check_references_constraints( foreign->n_fields))) { if (foreign->foreign_table == NULL) { - dict_table_get(foreign->foreign_table_name); + dict_table_get(foreign->foreign_table_name, + FALSE); } if (foreign->foreign_table) { diff --git a/storage/innobase/srv/srv0start.c b/storage/innobase/srv/srv0start.c index 5eaea26b75d..25f6f05e878 100644 --- a/storage/innobase/srv/srv0start.c +++ b/storage/innobase/srv/srv0start.c @@ -1601,17 +1601,6 @@ innobase_start_or_create_for_mysql(void) srv_was_started = TRUE; srv_is_being_started = FALSE; -#ifdef UNIV_DEBUG - /* Wait a while so that the created threads have time to suspend - themselves before we switch sync debugging on; otherwise a thread may - execute mutex_enter() before the checks are on, and mutex_exit() after - the checks are on, which will cause an assertion failure in sync - debug. */ - - os_thread_sleep(3000000); -#endif - sync_order_checks_on = TRUE; - if (trx_doublewrite == NULL) { /* Create the doublewrite buffer to a new tablespace */ diff --git a/storage/innobase/sync/sync0rw.c b/storage/innobase/sync/sync0rw.c index 441933843d7..549ad36271b 100644 --- a/storage/innobase/sync/sync0rw.c +++ b/storage/innobase/sync/sync0rw.c @@ -89,11 +89,14 @@ void rw_lock_create_func( /*================*/ rw_lock_t* lock, /* in: pointer to memory */ - ulint level __attribute__((unused)), - /* in: level */ +#ifdef UNIV_DEBUG +# ifdef UNIV_SYNC_DEBUG + ulint level, /* in: level */ +# endif /* UNIV_SYNC_DEBUG */ + 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 */ - const char* cmutex_name) /* in: mutex name */ + ulint cline) /* in: file line where created */ { /* If this is the very first time a synchronization object is created, then the following call initializes the sync system. */ @@ -103,10 +106,10 @@ rw_lock_create_func( lock->mutex.cfile_name = cfile_name; lock->mutex.cline = cline; -#ifndef UNIV_HOTBACKUP +#if defined UNIV_DEBUG && !defined UNIV_HOTBACKUP lock->mutex.cmutex_name = cmutex_name; lock->mutex.mutex_type = 1; -#endif /* !UNIV_HOTBACKUP */ +#endif /* UNIV_DEBUG && !UNIV_HOTBACKUP */ rw_lock_set_waiters(lock, 0); rw_lock_set_writer(lock, RW_LOCK_NOT_LOCKED); diff --git a/storage/innobase/sync/sync0sync.c b/storage/innobase/sync/sync0sync.c index ff7056b0afe..c0198469491 100644 --- a/storage/innobase/sync/sync0sync.c +++ b/storage/innobase/sync/sync0sync.c @@ -108,8 +108,6 @@ will set the waiters field to 0 in mutex_exit, and then call sync_array_signal_object with the mutex as an argument. Q.E.D. */ -ulint sync_dummy = 0; - /* The number of system calls made in this module. Intended for performance monitoring. */ @@ -133,6 +131,7 @@ ibool sync_initialized = FALSE; typedef struct sync_level_struct sync_level_t; typedef struct sync_thread_struct sync_thread_t; +#ifdef UNIV_SYNC_DEBUG /* The latch levels currently owned by threads are stored in this data structure; the size of this array is OS_THREAD_MAX_N */ @@ -140,6 +139,7 @@ sync_thread_t* sync_thread_level_arrays; /* Mutex protecting sync_thread_level_arrays */ mutex_t sync_thread_mutex; +#endif /* UNIV_SYNC_DEBUG */ /* Global list of database mutexes (not OS mutexes) created. */ ut_list_base_node_t mutex_list; @@ -147,11 +147,10 @@ ut_list_base_node_t mutex_list; /* Mutex protecting the mutex_list variable */ mutex_t mutex_list_mutex; +#ifdef UNIV_SYNC_DEBUG /* Latching order checks start when this is set TRUE */ ibool sync_order_checks_on = FALSE; - -/* Dummy mutex used to implement mutex_fence */ -mutex_t dummy_mutex_for_fence; +#endif /* UNIV_SYNC_DEBUG */ struct sync_thread_struct{ os_thread_id_t id; /* OS thread id */ @@ -202,10 +201,14 @@ void mutex_create_func( /*==============*/ mutex_t* mutex, /* in: pointer to memory */ +#ifdef UNIV_DEBUG + const char* cmutex_name, /* in: mutex name */ +# ifdef UNIV_SYNC_DEBUG ulint level, /* in: level */ +# endif /* UNIV_SYNC_DEBUG */ +#endif /* UNIV_DEBUG */ const char* cfile_name, /* in: file name where created */ - ulint cline, /* in: file line where created */ - const char* cmutex_name) /* in: mutex name */ + ulint cline) /* in: file line where created */ { #if defined(_WIN32) && defined(UNIV_CAN_USE_X86_ASSEMBLER) mutex_reset_lock_word(mutex); @@ -214,15 +217,19 @@ mutex_create_func( mutex->lock_word = 0; #endif mutex_set_waiters(mutex, 0); +#ifdef UNIV_DEBUG mutex->magic_n = MUTEX_MAGIC_N; +#endif /* UNIV_DEBUG */ #ifdef UNIV_SYNC_DEBUG mutex->line = 0; mutex->file_name = "not yet reserved"; -#endif /* UNIV_SYNC_DEBUG */ mutex->level = level; +#endif /* UNIV_SYNC_DEBUG */ mutex->cfile_name = cfile_name; mutex->cline = cline; #ifndef UNIV_HOTBACKUP + mutex->count_os_wait = 0; +# ifdef UNIV_DEBUG mutex->cmutex_name= cmutex_name; mutex->count_using= 0; mutex->mutex_type= 0; @@ -230,8 +237,8 @@ mutex_create_func( mutex->lmax_spent_time= 0; mutex->count_spin_loop= 0; mutex->count_spin_rounds= 0; - mutex->count_os_wait= 0; mutex->count_os_yield= 0; +# endif /* UNIV_DEBUG */ #endif /* !UNIV_HOTBACKUP */ /* Check that lock_word is aligned; this is important on Intel */ @@ -239,16 +246,19 @@ mutex_create_func( /* NOTE! The very first mutexes are not put to the mutex list */ - if ((mutex == &mutex_list_mutex) || (mutex == &sync_thread_mutex)) { + if ((mutex == &mutex_list_mutex) +#ifdef UNIV_SYNC_DEBUG + || (mutex == &sync_thread_mutex) +#endif /* UNIV_SYNC_DEBUG */ + ) { return; } mutex_enter(&mutex_list_mutex); - if (UT_LIST_GET_LEN(mutex_list) > 0) { - ut_a(UT_LIST_GET_FIRST(mutex_list)->magic_n == MUTEX_MAGIC_N); - } + ut_ad(UT_LIST_GET_LEN(mutex_list) == 0 + || UT_LIST_GET_FIRST(mutex_list)->magic_n == MUTEX_MAGIC_N); UT_LIST_ADD_FIRST(list, mutex_list, mutex); @@ -265,24 +275,24 @@ mutex_free( /*=======*/ mutex_t* mutex) /* in: mutex */ { -#ifdef UNIV_DEBUG - ut_a(mutex_validate(mutex)); -#endif /* UNIV_DEBUG */ + ut_ad(mutex_validate(mutex)); ut_a(mutex_get_lock_word(mutex) == 0); ut_a(mutex_get_waiters(mutex) == 0); - if (mutex != &mutex_list_mutex && mutex != &sync_thread_mutex) { + if (mutex != &mutex_list_mutex +#ifdef UNIV_SYNC_DEBUG + && mutex != &sync_thread_mutex +#endif /* UNIV_SYNC_DEBUG */ + ) { mutex_enter(&mutex_list_mutex); - if (UT_LIST_GET_PREV(list, mutex)) { - ut_a(UT_LIST_GET_PREV(list, mutex)->magic_n - == MUTEX_MAGIC_N); - } - if (UT_LIST_GET_NEXT(list, mutex)) { - ut_a(UT_LIST_GET_NEXT(list, mutex)->magic_n - == MUTEX_MAGIC_N); - } + ut_ad(!UT_LIST_GET_PREV(list, mutex) + || UT_LIST_GET_PREV(list, mutex)->magic_n + == MUTEX_MAGIC_N); + ut_ad(!UT_LIST_GET_NEXT(list, mutex) + || UT_LIST_GET_NEXT(list, mutex)->magic_n + == MUTEX_MAGIC_N); UT_LIST_REMOVE(list, mutex_list, mutex); @@ -295,8 +305,9 @@ mutex_free( /* If we free the mutex protecting the mutex list (freeing is not necessary), we have to reset the magic number AFTER removing it from the list. */ - +#ifdef UNIV_DEBUG mutex->magic_n = 0; +#endif /* UNIV_DEBUG */ } /************************************************************************ @@ -328,6 +339,7 @@ mutex_enter_nowait( return(1); } +#ifdef UNIV_DEBUG /********************************************************************** Checks that the mutex has been initialized. */ @@ -341,6 +353,7 @@ mutex_validate( return(TRUE); } +#endif /* UNIV_DEBUG */ /********************************************************************** Sets the waiters field in a mutex. */ @@ -376,13 +389,13 @@ mutex_spin_wait( { ulint index; /* index of the reserved wait cell */ ulint i; /* spin round count */ -#ifndef UNIV_HOTBACKUP +#if defined UNIV_DEBUG && !defined UNIV_HOTBACKUP ib_longlong lstart_time = 0, lfinish_time; /* for timing os_wait */ ulint ltime_diff; ulint sec; ulint ms; uint timer_started = 0; -#endif /* !UNIV_HOTBACKUP */ +#endif /* UNIV_DEBUG && !UNIV_HOTBACKUP */ ut_ad(mutex); mutex_loop: @@ -396,10 +409,10 @@ mutex_loop: a memory word. */ spin_loop: -#ifndef UNIV_HOTBACKUP +#if defined UNIV_DEBUG && !defined UNIV_HOTBACKUP mutex_spin_wait_count++; mutex->count_spin_loop++; -#endif /* !UNIV_HOTBACKUP */ +#endif /* UNIV_DEBUG && !UNIV_HOTBACKUP */ while (mutex_get_lock_word(mutex) != 0 && i < SYNC_SPIN_ROUNDS) { if (srv_spin_wait_delay) { @@ -410,14 +423,14 @@ spin_loop: } if (i == SYNC_SPIN_ROUNDS) { -#ifndef UNIV_HOTBACKUP +#if defined UNIV_DEBUG && !defined UNIV_HOTBACKUP mutex->count_os_yield++; if (timed_mutexes == 1 && timer_started==0) { ut_usectime(&sec, &ms); lstart_time= (ib_longlong)sec * 1000000 + ms; timer_started = 1; } -#endif /* !UNIV_HOTBACKUP */ +#endif /* UNIV_DEBUG && !UNIV_HOTBACKUP */ os_thread_yield(); } @@ -431,9 +444,9 @@ spin_loop: mutex_spin_round_count += i; -#ifndef UNIV_HOTBACKUP +#if defined UNIV_DEBUG && !defined UNIV_HOTBACKUP mutex->count_spin_rounds += i; -#endif /* !UNIV_HOTBACKUP */ +#endif /* UNIV_DEBUG && !UNIV_HOTBACKUP */ if (mutex_test_and_set(mutex) == 0) { /* Succeeded! */ @@ -514,6 +527,7 @@ spin_loop: #ifndef UNIV_HOTBACKUP mutex->count_os_wait++; +# ifdef UNIV_DEBUG /* !!!!! Sometimes os_wait can be called without os_thread_yield */ if (timed_mutexes == 1 && timer_started==0) { @@ -521,13 +535,14 @@ spin_loop: lstart_time= (ib_longlong)sec * 1000000 + ms; timer_started = 1; } +# endif /* UNIV_DEBUG */ #endif /* !UNIV_HOTBACKUP */ sync_array_wait_event(sync_primary_wait_array, index); goto mutex_loop; finish_timing: -#ifndef UNIV_HOTBACKUP +#if defined UNIV_DEBUG && !defined UNIV_HOTBACKUP if (timed_mutexes == 1 && timer_started==1) { ut_usectime(&sec, &ms); lfinish_time= (ib_longlong)sec * 1000000 + ms; @@ -539,7 +554,7 @@ finish_timing: mutex->lmax_spent_time= ltime_diff; } } -#endif /* !UNIV_HOTBACKUP */ +#endif /* UNIV_DEBUG && !UNIV_HOTBACKUP */ return; } @@ -598,9 +613,7 @@ mutex_get_debug_info( *line = mutex->line; *thread_id = mutex->thread_id; } -#endif /* UNIV_SYNC_DEBUG */ -#ifdef UNIV_SYNC_DEBUG /********************************************************************** Checks that the current thread owns the mutex. Works only in the debug version. */ @@ -611,7 +624,7 @@ mutex_own( /* out: TRUE if owns */ mutex_t* mutex) /* in: mutex */ { - ut_a(mutex_validate(mutex)); + ut_ad(mutex_validate(mutex)); if (mutex_get_lock_word(mutex) != 1) { @@ -710,7 +723,6 @@ sync_all_freed(void) { return(mutex_n_reserved() + rw_lock_n_locked() == 0); } -#endif /* UNIV_SYNC_DEBUG */ /********************************************************************** Gets the value in the nth slot in the thread level arrays. */ @@ -834,7 +846,6 @@ sync_thread_levels_g( (ulong) mutex->cline); if (mutex_get_lock_word(mutex) != 0) { -#ifdef UNIV_SYNC_DEBUG const char* file_name; ulint line; os_thread_id_t thread_id; @@ -852,19 +863,11 @@ sync_thread_levels_g( thread_id), file_name, (ulong) line); -#else /* UNIV_SYNC_DEBUG */ - fprintf(stderr, - "InnoDB: Locked mutex:" - " addr %p\n", - (void*) mutex); -#endif /* UNIV_SYNC_DEBUG */ } else { fputs("Not locked\n", stderr); } } else { -#ifdef UNIV_SYNC_DEBUG rw_lock_print(lock); -#endif /* UNIV_SYNC_DEBUG */ } return(FALSE); @@ -996,9 +999,7 @@ sync_thread_add_level( if ((latch == (void*)&sync_thread_mutex) || (latch == (void*)&mutex_list_mutex) -#ifdef UNIV_SYNC_DEBUG || (latch == (void*)&rw_lock_debug_mutex) -#endif /* UNIV_SYNC_DEBUG */ || (latch == (void*)&rw_lock_list_mutex)) { return; @@ -1219,9 +1220,7 @@ sync_thread_reset_level( if ((latch == (void*)&sync_thread_mutex) || (latch == (void*)&mutex_list_mutex) -#ifdef UNIV_SYNC_DEBUG || (latch == (void*)&rw_lock_debug_mutex) -#endif /* UNIV_SYNC_DEBUG */ || (latch == (void*)&rw_lock_list_mutex)) { return(FALSE); @@ -1260,6 +1259,7 @@ sync_thread_reset_level( return(FALSE); } +#endif /* UNIV_SYNC_DEBUG */ /********************************************************************** Initializes the synchronization data structures. */ @@ -1268,8 +1268,10 @@ void sync_init(void) /*===========*/ { +#ifdef UNIV_SYNC_DEBUG sync_thread_t* thread_slot; ulint i; +#endif /* UNIV_SYNC_DEBUG */ ut_a(sync_initialized == FALSE); @@ -1280,7 +1282,7 @@ sync_init(void) sync_primary_wait_array = sync_array_create(OS_THREAD_MAX_N, SYNC_ARRAY_OS_MUTEX); - +#ifdef UNIV_SYNC_DEBUG /* Create the thread latch level array where the latch levels are stored for each OS thread */ @@ -1291,13 +1293,14 @@ sync_init(void) thread_slot = sync_thread_level_arrays_get_nth(i); thread_slot->levels = NULL; } - +#endif /* UNIV_SYNC_DEBUG */ /* 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); - +#ifdef UNIV_SYNC_DEBUG mutex_create(&sync_thread_mutex, SYNC_NO_ORDER_CHECK); +#endif /* UNIV_SYNC_DEBUG */ /* Init the rw-lock list and create the mutex to protect it. */ @@ -1332,7 +1335,9 @@ sync_close(void) } mutex_free(&mutex_list_mutex); +#ifdef UNIV_SYNC_DEBUG mutex_free(&sync_thread_mutex); +#endif /* UNIV_SYNC_DEBUG */ } /*********************************************************************** diff --git a/storage/innobase/trx/trx0roll.c b/storage/innobase/trx/trx0roll.c index 1b00ae63ecd..201d1be3656 100644 --- a/storage/innobase/trx/trx0roll.c +++ b/storage/innobase/trx/trx0roll.c @@ -131,8 +131,26 @@ trx_rollback_for_mysql( trx->op_info = "rollback"; - err = trx_general_rollback_for_mysql(trx, FALSE, NULL); + /* If we are doing the XA recovery of prepared transactions, then + the transaction object does not have an InnoDB session object, and we + set a dummy session that we use for all MySQL transactions. */ + + mutex_enter(&kernel_mutex); + + if (trx->sess == NULL) { + /* Open a dummy session */ + + if (!trx_dummy_sess) { + trx_dummy_sess = sess_open(); + } + trx->sess = trx_dummy_sess; + } + + mutex_exit(&kernel_mutex); + + err = trx_general_rollback_for_mysql(trx, FALSE, NULL); + trx->op_info = ""; return(err); diff --git a/storage/innobase/trx/trx0trx.c b/storage/innobase/trx/trx0trx.c index 4d0a26b5757..cfa2b01f406 100644 --- a/storage/innobase/trx/trx0trx.c +++ b/storage/innobase/trx/trx0trx.c @@ -1598,6 +1598,24 @@ trx_commit_for_mysql( trx->op_info = "committing"; + /* If we are doing the XA recovery of prepared transactions, then + the transaction object does not have an InnoDB session object, and we + set the dummy session that we use for all MySQL transactions. */ + + mutex_enter(&kernel_mutex); + + if (trx->sess == NULL) { + /* Open a dummy session */ + + if (!trx_dummy_sess) { + trx_dummy_sess = sess_open(); + } + + trx->sess = trx_dummy_sess; + } + + mutex_exit(&kernel_mutex); + trx_start_if_not_started(trx); mutex_enter(&kernel_mutex); @@ -1761,11 +1779,10 @@ trx_print( || mem_heap_get_size(trx->lock_heap) > 400) { newline = TRUE; - fprintf(f, "%lu lock struct(s), heap size %lu", + fprintf(f, "%lu lock struct(s), heap size %lu," + " %lu row lock(s)", (ulong) UT_LIST_GET_LEN(trx->trx_locks), - (ulong) mem_heap_get_size(trx->lock_heap)); - - fprintf(f, "%lu row lock(s)", + (ulong) mem_heap_get_size(trx->lock_heap), (ulong) lock_number_of_rows_locked(trx)); } |