diff options
author | Aleksandr Kuzminsky <aleksandr.kuzminsky@percona.com> | 2009-09-30 18:33:51 +0000 |
---|---|---|
committer | Aleksandr Kuzminsky <aleksandr.kuzminsky@percona.com> | 2009-09-30 18:33:51 +0000 |
commit | 2bde0c5e6d31583e5197e3b513f572a693161f62 (patch) | |
tree | 15efc5a928e2717a27094a06b31608be466cd2a6 | |
parent | 9a591471e07dea844580d782b40d83365bcd4747 (diff) | |
download | mariadb-git-2bde0c5e6d31583e5197e3b513f572a693161f62.tar.gz |
Sync with rev. 107
-rw-r--r-- | handler/ha_innodb.cc | 20 | ||||
-rw-r--r-- | handler/innodb_patch_info.h | 1 | ||||
-rw-r--r-- | include/srv0srv.h | 12 | ||||
-rw-r--r-- | srv/srv0srv.c | 75 | ||||
-rw-r--r-- | srv/srv0start.c | 11 |
5 files changed, 115 insertions, 4 deletions
diff --git a/handler/ha_innodb.cc b/handler/ha_innodb.cc index 51369a44b03..2d05f4936a6 100644 --- a/handler/ha_innodb.cc +++ b/handler/ha_innodb.cc @@ -206,6 +206,7 @@ static my_bool innobase_use_doublewrite = TRUE; static my_bool innobase_use_checksums = TRUE; static my_bool innobase_extra_undoslots = FALSE; static my_bool innobase_fast_recovery = FALSE; +static my_bool innobase_use_purge_thread = FALSE; static my_bool innobase_locks_unsafe_for_binlog = FALSE; static my_bool innobase_overwrite_relay_log_info = FALSE; static my_bool innobase_rollback_on_timeout = FALSE; @@ -2293,6 +2294,8 @@ innobase_change_buffering_inited_ok: srv_fast_recovery = (ibool) innobase_fast_recovery; + srv_use_purge_thread = (ibool) innobase_use_purge_thread; + srv_use_doublewrite_buf = (ibool) innobase_use_doublewrite; srv_use_checksums = (ibool) innobase_use_checksums; @@ -7268,7 +7271,7 @@ ha_innobase::info( We do not update delete_length if no locking is requested so the "old" value can remain. delete_length is initialized to 0 in the ha_statistics' constructor. */ - if (!(flag & HA_STATUS_NO_LOCK)) { + if (!(flag & HA_STATUS_NO_LOCK) && srv_stats_update_need_lock) { /* lock the data dictionary to avoid races with ibd_file_missing and tablespace_discarded */ @@ -9934,6 +9937,11 @@ static MYSQL_SYSVAR_BOOL(fast_recovery, innobase_fast_recovery, "Enable to use speed hack of recovery avoiding flush list sorting.", NULL, NULL, FALSE); +static MYSQL_SYSVAR_BOOL(use_purge_thread, innobase_use_purge_thread, + PLUGIN_VAR_NOCMDARG | PLUGIN_VAR_READONLY, + "Enable to use purge devoted thread.", + NULL, NULL, FALSE); + static MYSQL_SYSVAR_BOOL(overwrite_relay_log_info, innobase_overwrite_relay_log_info, PLUGIN_VAR_NOCMDARG | PLUGIN_VAR_READONLY, "During InnoDB crash recovery on slave overwrite relay-log.info " @@ -10081,6 +10089,12 @@ static MYSQL_SYSVAR_ULONG(stats_auto_update, srv_stats_auto_update, "(except for ANALYZE TABLE command) 0:disable 1:enable", NULL, NULL, 1, 0, 1, 0); +static MYSQL_SYSVAR_ULONG(stats_update_need_lock, srv_stats_update_need_lock, + PLUGIN_VAR_RQCMDARG, + "Enable/Disable InnoDB's update statistics which needs to lock dictionary. " + "e.g. Data_free.", + NULL, NULL, 1, 0, 1, 0); + static MYSQL_SYSVAR_BOOL(adaptive_hash_index, btr_search_enabled, PLUGIN_VAR_OPCMDARG, "Enable InnoDB adaptive hash index (enabled by default). " @@ -10325,7 +10339,7 @@ static MYSQL_SYSVAR_ULONG(expand_import, srv_expand_import, static MYSQL_SYSVAR_ULONG(extra_rsegments, srv_extra_rsegments, PLUGIN_VAR_RQCMDARG | PLUGIN_VAR_READONLY, "Number of extra user rollback segments when create new database.", - NULL, NULL, 0, 0, 127, 0); + NULL, NULL, 0, 0, 126, 0); static MYSQL_SYSVAR_ULONG(dict_size_limit, srv_dict_size_limit, PLUGIN_VAR_RQCMDARG, @@ -10374,6 +10388,7 @@ static struct st_mysql_sys_var* innobase_system_variables[]= { MYSQL_SYSVAR(stats_on_metadata), MYSQL_SYSVAR(stats_method), MYSQL_SYSVAR(stats_auto_update), + MYSQL_SYSVAR(stats_update_need_lock), MYSQL_SYSVAR(stats_sample_pages), MYSQL_SYSVAR(adaptive_hash_index), MYSQL_SYSVAR(replication_delay), @@ -10404,6 +10419,7 @@ static struct st_mysql_sys_var* innobase_system_variables[]= { MYSQL_SYSVAR(change_buffering), MYSQL_SYSVAR(read_ahead_threshold), MYSQL_SYSVAR(io_capacity), + MYSQL_SYSVAR(use_purge_thread), NULL }; diff --git a/handler/innodb_patch_info.h b/handler/innodb_patch_info.h index 645e745ff41..f8a728d0d27 100644 --- a/handler/innodb_patch_info.h +++ b/handler/innodb_patch_info.h @@ -37,5 +37,6 @@ struct innodb_enhancement { {"innodb_split_buf_pool_mutex","More fix of buffer_pool mutex","Spliting buf_pool_mutex and optimizing based on innodb_opt_lru_count","http://www.percona.com/docs/wiki/percona-xtradb"}, {"innodb_stats","Additional features about InnoDB statistics/optimizer","","http://www.percona.com/docs/wiki/percona-xtradb"}, {"innodb_recovery_patches","Bugfixes and adjustments about recovery process","","http://www.percona.com/docs/wiki/percona-xtradb"}, +{"innodb_purge_thread","Enable to use purge devoted thread","","http://www.percona.com/docs/wiki/percona-xtradb"}, {NULL, NULL, NULL, NULL} }; diff --git a/include/srv0srv.h b/include/srv0srv.h index 9a7587f8cb3..ac409e1093d 100644 --- a/include/srv0srv.h +++ b/include/srv0srv.h @@ -134,6 +134,8 @@ extern ibool srv_extra_undoslots; extern ibool srv_fast_recovery; +extern ibool srv_use_purge_thread; + extern ibool srv_auto_extend_last_data_file; extern ulint srv_last_file_size_max; extern char** srv_log_group_home_dirs; @@ -217,6 +219,7 @@ extern ulint srv_stats_method; #define SRV_STATS_METHOD_NULLS_NOT_EQUAL 1 #define SRV_STATS_METHOD_IGNORE_NULLS 2 extern ulint srv_stats_auto_update; +extern ulint srv_stats_update_need_lock; extern ibool srv_use_doublewrite_buf; extern ibool srv_use_checksums; @@ -424,6 +427,7 @@ enum srv_thread_type { SRV_RECOVERY, /**< threads finishing a recovery */ SRV_INSERT, /**< thread flushing the insert buffer to disk */ #endif + SRV_PURGE, /* thread purging undo records */ SRV_MASTER /**< the master thread, (whose type number must be biggest) */ }; @@ -497,6 +501,14 @@ srv_master_thread( /*==============*/ void* arg); /*!< in: a dummy parameter required by os_thread_create */ +/************************************************************************* +The undo purge thread. */ +UNIV_INTERN +os_thread_ret_t +srv_purge_thread( +/*=============*/ + void* arg); /* in: a dummy parameter required by + os_thread_create */ /*******************************************************************//** Tells the Innobase server that there has been activity in the database and wakes up the master thread if it is suspended (not sleeping). Used diff --git a/srv/srv0srv.c b/srv/srv0srv.c index 3c9b5fbe825..2cfc852dc5c 100644 --- a/srv/srv0srv.c +++ b/srv/srv0srv.c @@ -162,6 +162,8 @@ UNIV_INTERN ibool srv_extra_undoslots = FALSE; UNIV_INTERN ibool srv_fast_recovery = FALSE; +UNIV_INTERN ibool srv_use_purge_thread = FALSE; + /* if TRUE, then we auto-extend the last data file */ UNIV_INTERN ibool srv_auto_extend_last_data_file = FALSE; /* if != 0, this tells the max size auto-extending may increase the @@ -381,6 +383,7 @@ this many index pages */ UNIV_INTERN unsigned long long srv_stats_sample_pages = 8; UNIV_INTERN ulint srv_stats_method = 0; UNIV_INTERN ulint srv_stats_auto_update = 1; +UNIV_INTERN ulint srv_stats_update_need_lock = 1; UNIV_INTERN ibool srv_use_doublewrite_buf = TRUE; UNIV_INTERN ibool srv_use_checksums = TRUE; @@ -2736,7 +2739,7 @@ loop: lsn_old = log_sys->lsn; mutex_exit(&(log_sys->mutex)); } else if ((log_sys->lsn - oldest_lsn) - > (log_sys->max_checkpoint_age)/2 ) { + > (log_sys->max_checkpoint_age)/4 ) { /* defence line (max_checkpoint_age * 1/2) */ ib_uint64_t lsn = log_sys->lsn; @@ -2772,7 +2775,7 @@ loop: if (!srv_use_doublewrite_buf) { /* flush is faster than when doublewrite */ - bpl = (bpl * 3) / 4; + bpl = (bpl * 7) / 8; } if (bpl) { @@ -2856,6 +2859,7 @@ retry_flush_batch: /* Flush logs if needed */ srv_sync_log_buffer_in_background(); + if (!srv_use_purge_thread) { /* We run a full purge every 10 seconds, even if the server were active */ do { @@ -2872,6 +2876,7 @@ retry_flush_batch: srv_sync_log_buffer_in_background(); } while (n_pages_purged); + } srv_main_thread_op_info = "flushing buffer pool pages"; @@ -2940,6 +2945,7 @@ background_loop: os_thread_sleep(100000); } + if (!srv_use_purge_thread) { srv_main_thread_op_info = "purging"; /* Run a full purge */ @@ -2956,6 +2962,7 @@ background_loop: srv_sync_log_buffer_in_background(); } while (n_pages_purged); + } srv_main_thread_op_info = "reserving kernel mutex"; @@ -3108,3 +3115,67 @@ suspend_thread: OS_THREAD_DUMMY_RETURN; /* Not reached, avoid compiler warning */ } + +/************************************************************************* +A thread which is devoted to purge, for take over the master thread's +purging */ +UNIV_INTERN +os_thread_ret_t +srv_purge_thread( +/*=============*/ + void* arg __attribute__((unused))) + /* in: a dummy parameter required by os_thread_create */ +{ + ulint n_pages_purged; + ulint n_pages_purged_sum = 1; /* dummy */ + ulint history_len; + ulint sleep_ms= 10000; /* initial: 10 sec. */ + +#ifdef UNIV_DEBUG_THREAD_CREATION + fprintf(stderr, "Purge thread starts, id %lu\n", + os_thread_pf(os_thread_get_curr_id())); +#endif + + srv_table_reserve_slot(SRV_PURGE); + mutex_enter(&kernel_mutex); + srv_n_threads_active[SRV_PURGE]++; + mutex_exit(&kernel_mutex); + +loop: + if (srv_fast_shutdown && srv_shutdown_state > 0) { + goto exit_func; + } + + os_thread_sleep( sleep_ms * 1000 ); + + history_len = trx_sys->rseg_history_len; + if (history_len > 1000) + sleep_ms /= 10; + if (sleep_ms < 10) + sleep_ms = 10; + + n_pages_purged_sum = 0; + + do { + if (srv_fast_shutdown && srv_shutdown_state > 0) { + goto exit_func; + } + n_pages_purged = trx_purge(); + n_pages_purged_sum += n_pages_purged; + } while (n_pages_purged); + + if (n_pages_purged_sum == 0) + sleep_ms *= 10; + if (sleep_ms > 10000) + sleep_ms = 10000; + + goto loop; + +exit_func: + /* We count the number of threads in os_thread_exit(). A created + thread should always use that to exit and not use return() to exit. */ + + os_thread_exit(NULL); + + OS_THREAD_DUMMY_RETURN; +} diff --git a/srv/srv0start.c b/srv/srv0start.c index b94a9e12a16..e8a9dabdc41 100644 --- a/srv/srv0start.c +++ b/srv/srv0start.c @@ -1544,6 +1544,12 @@ innobase_start_or_create_for_mysql(void) dict_create(); srv_startup_is_before_trx_rollback_phase = FALSE; + if (trx_doublewrite == NULL) { + /* Create the doublewrite buffer here to avoid assertion error + about page_no of doublewrite_buf */ + trx_sys_create_doublewrite_buf(); + } + if (srv_extra_rsegments) trx_sys_create_extra_rseg(srv_extra_rsegments); #ifdef UNIV_LOG_ARCHIVE @@ -1731,6 +1737,11 @@ innobase_start_or_create_for_mysql(void) os_thread_create(&srv_master_thread, NULL, thread_ids + (1 + SRV_MAX_N_IO_THREADS)); + + if (srv_use_purge_thread) { + os_thread_create(&srv_purge_thread, NULL, thread_ids + + (4 + SRV_MAX_N_IO_THREADS)); + } #ifdef UNIV_DEBUG /* buf_debug_prints = TRUE; */ #endif /* UNIV_DEBUG */ |