From d17ecff410180adf96dcd7f261157d52e7f62af2 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jan=20Lindstr=C3=B6m?= Date: Thu, 13 Feb 2014 09:13:56 +0200 Subject: [PATCH] Fixed issue on data dictionary corruption. Fixed issue on multi-threaded flush at shutdown. Removed unnecessary startup option innodb_compress_pages. Added a new startup option innodb_mtflush_threads, default 8. --- storage/innobase/buf/buf0mtflu.cc | 37 +++++++++++++++------------ storage/innobase/handler/ha_innodb.cc | 24 ++++++++--------- storage/innobase/include/dict0dict.ic | 19 +++++++++----- storage/innobase/include/fsp0fsp.ic | 22 +++++++++++++--- storage/innobase/include/srv0srv.h | 4 +-- storage/innobase/os/os0file.cc | 3 ++- storage/innobase/srv/srv0srv.cc | 5 +--- storage/innobase/srv/srv0start.cc | 11 +++----- storage/xtradb/buf/buf0mtflu.cc | 37 +++++++++++++++------------ storage/xtradb/handler/ha_innodb.cc | 24 ++++++++--------- storage/xtradb/include/dict0dict.ic | 19 +++++++++----- storage/xtradb/include/fsp0fsp.ic | 22 +++++++++++++--- storage/xtradb/include/srv0srv.h | 4 +-- storage/xtradb/os/os0file.cc | 3 ++- storage/xtradb/srv/srv0srv.cc | 5 +--- storage/xtradb/srv/srv0start.cc | 12 ++++----- 16 files changed, 141 insertions(+), 110 deletions(-) diff --git a/storage/innobase/buf/buf0mtflu.cc b/storage/innobase/buf/buf0mtflu.cc index a28b1885fe4..fb1d1ce54ae 100644 --- a/storage/innobase/buf/buf0mtflu.cc +++ b/storage/innobase/buf/buf0mtflu.cc @@ -272,7 +272,7 @@ mtflush_service_io( { wrk_t *work_item = NULL; ulint n_flushed=0; - ib_time_t max_wait_usecs = 5000000; + ib_time_t max_wait_usecs = 50000; mtflush_io->wt_status = WTHR_SIG_WAITING; work_item = (wrk_t *)ib_wqueue_timedwait(mtflush_io->wq, max_wait_usecs); @@ -300,7 +300,8 @@ mtflush_service_io( ut_a(work_item->wi_status == WRK_ITEM_EXIT); work_item->wi_status = WRK_ITEM_EXIT; ib_wqueue_add(mtflush_io->wr_cq, work_item, mtflush_io->wheap); - break; + mtflush_io->wt_status = WTHR_KILL_IT; + return; case MT_WRK_WRITE: work_item->wi_status = WRK_ITEM_START; @@ -346,11 +347,11 @@ DECLARE_THREAD(mtflush_io_thread)( #ifdef UNIV_DEBUG ib_uint64_t stat_universal_num_processed = 0; ib_uint64_t stat_cycle_num_processed = 0; - wrk_t* work_item = mtflush_io[0].work_item; + wrk_t* work_item = mtflush_io[0].work_item; ulint i; #endif - while (srv_shutdown_state != SRV_SHUTDOWN_EXIT_THREADS) { + while (TRUE) { mtflush_service_io(mtflush_io); #ifdef UNIV_DEBUG @@ -365,12 +366,9 @@ DECLARE_THREAD(mtflush_io_thread)( stat_cycle_num_processed); mtflu_print_thread_stat(work_item); #endif - } - - /* This should make sure that all current work items are - processed before threads exit. */ - while (!ib_wqueue_is_empty(mtflush_io->wq)) { - mtflush_service_io(mtflush_io); + if (mtflush_io->wt_status == WTHR_KILL_IT) { + break; + } } os_thread_exit(NULL); @@ -385,16 +383,21 @@ void buf_mtflu_io_thread_exit(void) /*==========================*/ { - ulint i; + long i; thread_sync_t* mtflush_io = mtflush_ctx; ut_a(mtflush_io != NULL); - fprintf(stderr, "signal page_comp_io_threads to exit [%lu]\n", + /* Confirm if the io-thread KILL is in progress, bailout */ + if (mtflush_io->wt_status == WTHR_KILL_IT) { + return; + } + + fprintf(stderr, "signal mtflush_io_threads to exit [%lu]\n", srv_buf_pool_instances); /* Send one exit work item/thread */ - for (i=0; i < srv_buf_pool_instances; i++) { + for (i=0; i < srv_mtflush_threads; i++) { mtflush_io->work_item[i].wr.buf_pool = NULL; mtflush_io->work_item[i].rd.page_pool = NULL; mtflush_io->work_item[i].tsk = MT_WRK_NONE; @@ -407,14 +410,14 @@ buf_mtflu_io_thread_exit(void) /* Wait until all work items on a work queue are processed */ while(!ib_wqueue_is_empty(mtflush_io->wq)) { - /* Wait about 1/2 sec */ - os_thread_sleep(50000); + /* Wait */ + os_thread_sleep(500000); } ut_a(ib_wqueue_is_empty(mtflush_io->wq)); /* Collect all work done items */ - for (i=0; i < srv_buf_pool_instances;) { + for (i=0; i < srv_mtflush_threads;) { wrk_t* work_item; work_item = (wrk_t *)ib_wqueue_timedwait(mtflush_io->wr_cq, 50000); @@ -558,11 +561,13 @@ buf_mtflu_flush_work_items( if((int)done_wi->id_usr == -1 && done_wi->wi_status == WRK_ITEM_SET ) { +#ifdef UNIV_DEBUG fprintf(stderr, "**Set/Unused work_item[%lu] flush_type=%d\n", i, done_wi->wr.flush_type); ut_ad(0); +#endif } n_flushed+= done_wi->n_flushed; diff --git a/storage/innobase/handler/ha_innodb.cc b/storage/innobase/handler/ha_innodb.cc index 812aa0cfe83..4999a202bd6 100644 --- a/storage/innobase/handler/ha_innodb.cc +++ b/storage/innobase/handler/ha_innodb.cc @@ -9769,14 +9769,6 @@ ha_innobase::check_table_options( /* Check page compression requirements */ if (options->page_compressed) { - if (!srv_compress_pages) { - push_warning( - thd, Sql_condition::WARN_LEVEL_WARN, - HA_WRONG_CREATE_OPTION, - "InnoDB: PAGE_COMPRESSED requires" - "innodb_compress_pages not enabled"); - return "PAGE_COMPRESSED"; - } if (row_format == ROW_TYPE_COMPRESSED) { push_warning( @@ -16587,11 +16579,6 @@ static MYSQL_SYSVAR_BOOL(trx_purge_view_update_only_debug, NULL, NULL, FALSE); #endif /* UNIV_DEBUG */ -static MYSQL_SYSVAR_BOOL(compress_pages, srv_compress_pages, - PLUGIN_VAR_NOCMDARG | PLUGIN_VAR_READONLY, - "Use page compression.", - NULL, NULL, FALSE); - static MYSQL_SYSVAR_LONG(trim_pct, srv_trim_pct, PLUGIN_VAR_OPCMDARG , "How many percent of compressed pages should be trimmed", @@ -16614,6 +16601,15 @@ static MYSQL_SYSVAR_BOOL(use_lz4, srv_use_lz4, NULL, NULL, FALSE); #endif /* HAVE_LZ4 */ +static MYSQL_SYSVAR_LONG(mtflush_threads, srv_mtflush_threads, + PLUGIN_VAR_RQCMDARG, + "Number of multi-threaded flush threads", + NULL, NULL, + MTFLUSH_DEFAULT_WORKER, /* Default setting */ + 1, /* Minimum setting */ + MTFLUSH_MAX_WORKER, /* Max setting */ + 0); + static struct st_mysql_sys_var* innobase_system_variables[]= { MYSQL_SYSVAR(additional_mem_pool_size), MYSQL_SYSVAR(api_trx_level), @@ -16759,13 +16755,13 @@ static struct st_mysql_sys_var* innobase_system_variables[]= { MYSQL_SYSVAR(limit_optimistic_insert_debug), MYSQL_SYSVAR(trx_purge_view_update_only_debug), #endif /* UNIV_DEBUG */ - MYSQL_SYSVAR(compress_pages), MYSQL_SYSVAR(trim_pct), MYSQL_SYSVAR(compress_index_pages), MYSQL_SYSVAR(use_trim), #ifdef HAVE_LZ4 MYSQL_SYSVAR(use_lz4), #endif + MYSQL_SYSVAR(mtflush_threads), NULL }; diff --git a/storage/innobase/include/dict0dict.ic b/storage/innobase/include/dict0dict.ic index 73fc9ac56fd..2be68e37dc8 100644 --- a/storage/innobase/include/dict0dict.ic +++ b/storage/innobase/include/dict0dict.ic @@ -700,7 +700,7 @@ dict_sys_tables_type_validate( if (redundant) { if (zip_ssize || atomic_blobs) { - fprintf(stderr, "InnoDB Error: SYS_TABLES::TYPE=Redundant, zip_ssize %lu atomic_blobs %lu\n", + fprintf(stderr, "InnoDB: Error: SYS_TABLES::TYPE=Redundant, zip_ssize %lu atomic_blobs %lu\n", zip_ssize, atomic_blobs); return(ULINT_UNDEFINED); } @@ -708,7 +708,7 @@ dict_sys_tables_type_validate( /* Make sure there are no bits that we do not know about. */ if (unused) { - fprintf(stderr, "InnoDB Error: SYS_TABLES::TYPE=%lu, unused %lu\n", + fprintf(stderr, "InnoDB: Error: SYS_TABLES::TYPE=%lu, unused %lu\n", type, unused); return(ULINT_UNDEFINED); } @@ -724,7 +724,7 @@ dict_sys_tables_type_validate( } else if (zip_ssize) { /* Antelope does not support COMPRESSED format. */ - fprintf(stderr, "InnoDB Error: SYS_TABLES::TYPE=%lu, zip_ssize %lu\n", + fprintf(stderr, "InnoDB: Error: SYS_TABLES::TYPE=%lu, zip_ssize %lu\n", type, zip_ssize); return(ULINT_UNDEFINED); } @@ -735,14 +735,14 @@ dict_sys_tables_type_validate( should be in N_COLS, but we already know about the low_order_bit and DICT_N_COLS_COMPACT flags. */ if (!atomic_blobs) { - fprintf(stderr, "InnoDB Error: SYS_TABLES::TYPE=%lu, zip_ssize %lu atomic_blobs %lu\n", + fprintf(stderr, "InnoDB: Error: SYS_TABLES::TYPE=%lu, zip_ssize %lu atomic_blobs %lu\n", type, zip_ssize, atomic_blobs); return(ULINT_UNDEFINED); } /* Validate that the number is within allowed range. */ if (zip_ssize > PAGE_ZIP_SSIZE_MAX) { - fprintf(stderr, "InnoDB Error: SYS_TABLES::TYPE=%lu, zip_ssize %lu max %d\n", + fprintf(stderr, "InnoDB: Error: SYS_TABLES::TYPE=%lu, zip_ssize %lu max %d\n", type, zip_ssize, PAGE_ZIP_SSIZE_MAX); return(ULINT_UNDEFINED); } @@ -760,13 +760,20 @@ dict_sys_tables_type_validate( low_order_bit and DICT_N_COLS_COMPACT flags. */ if (!atomic_blobs || !page_compression) { - fprintf(stderr, "InnoDB Error: SYS_TABLES::TYPE=%lu, page_compression %lu page_compression_level %lu\n" + fprintf(stderr, "InnoDB: Error: SYS_TABLES::TYPE=%lu, page_compression %lu page_compression_level %lu\n" "InnoDB: Error: atomic_blobs %lu\n", type, page_compression, page_compression_level, atomic_blobs); return(ULINT_UNDEFINED); } } + /* Validate that the atomic writes number is within allowed range. */ + if (atomic_writes < 0 || atomic_writes > ATOMIC_WRITES_OFF) { + fprintf(stderr, "InnoDB: Error: SYS_TABLES::TYPE=%lu, atomic_writes %lu\n", + type, atomic_writes); + return(ULINT_UNDEFINED); + } + /* Return the validated SYS_TABLES.TYPE. */ return(type); } diff --git a/storage/innobase/include/fsp0fsp.ic b/storage/innobase/include/fsp0fsp.ic index cb12d556ec4..fb253370b6e 100644 --- a/storage/innobase/include/fsp0fsp.ic +++ b/storage/innobase/include/fsp0fsp.ic @@ -67,13 +67,14 @@ fsp_flags_is_valid( ulint page_compression = FSP_FLAGS_GET_PAGE_COMPRESSION(flags); ulint page_compression_level = FSP_FLAGS_GET_PAGE_COMPRESSION_LEVEL(flags); ulint atomic_writes = FSP_FLAGS_GET_ATOMIC_WRITES(flags); - atomic_writes_t awrites = (atomic_writes_t)atomic_writes; DBUG_EXECUTE_IF("fsp_flags_is_valid_failure", return(false);); /* fsp_flags is zero unless atomic_blobs is set. */ /* Make sure there are no bits that we do not know about. */ if (unused != 0 || flags == 1) { + fprintf(stderr, "InnoDB: Error: Tablespace flags %lu corrupted unused %lu\n", + flags, unused); return(false); } else if (post_antelope) { /* The Antelope row formats REDUNDANT and COMPACT did @@ -81,6 +82,8 @@ fsp_flags_is_valid( 4-byte field is zero for Antelope row formats. */ if (!atomic_blobs) { + fprintf(stderr, "InnoDB: Error: Tablespace flags %lu corrupted atomic_blobs %lu\n", + flags, atomic_blobs); return(false); } } @@ -92,10 +95,14 @@ fsp_flags_is_valid( externally stored parts. */ if (post_antelope || zip_ssize != 0) { + fprintf(stderr, "InnoDB: Error: Tablespace flags %lu corrupted zip_ssize %lu atomic_blobs %lu\n", + flags, zip_ssize, atomic_blobs); return(false); } } else if (!post_antelope || zip_ssize > PAGE_ZIP_SSIZE_MAX) { + fprintf(stderr, "InnoDB: Error: Tablespace flags %lu corrupted zip_ssize %lu max %d\n", + flags, zip_ssize, PAGE_ZIP_SSIZE_MAX); return(false); } else if (page_ssize > UNIV_PAGE_SSIZE_MAX) { @@ -103,9 +110,13 @@ fsp_flags_is_valid( be zero for an original 16k page size. Validate the page shift size is within allowed range. */ + fprintf(stderr, "InnoDB: Error: Tablespace flags %lu corrupted page_ssize %lu max %lu\n", + flags, page_ssize, UNIV_PAGE_SSIZE_MAX); return(false); } else if (UNIV_PAGE_SIZE != UNIV_PAGE_SIZE_ORIG && !page_ssize) { + fprintf(stderr, "InnoDB: Error: Tablespace flags %lu corrupted page_ssize %lu max %lu:%d\n", + flags, page_ssize, UNIV_PAGE_SIZE, UNIV_PAGE_SIZE_ORIG); return(false); } @@ -113,13 +124,16 @@ fsp_flags_is_valid( to be set */ if (page_compression_level || page_compression) { if (!page_compression || !atomic_blobs) { + fprintf(stderr, "InnoDB: Error: Tablespace flags %lu corrupted page_compression %lu\n" + "InnoDB: Error: page_compression_level %lu atomic_blobs %lu\n", + flags, page_compression, page_compression_level, atomic_blobs); return(false); } } - if ((awrites == ATOMIC_WRITES_ON || - (awrites == ATOMIC_WRITES_DEFAULT && srv_use_atomic_writes)) - && !atomic_blobs) { + if (atomic_writes < 0 || atomic_writes > ATOMIC_WRITES_OFF) { + fprintf(stderr, "InnoDB: Error: Tablespace flags %lu corrupted atomic_writes %lu\n", + flags, atomic_writes); return (false); } diff --git a/storage/innobase/include/srv0srv.h b/storage/innobase/include/srv0srv.h index 0ffb966d9a3..725aaf9553d 100644 --- a/storage/innobase/include/srv0srv.h +++ b/storage/innobase/include/srv0srv.h @@ -236,9 +236,6 @@ use simulated aio we build below with threads. Currently we support native aio on windows and linux */ extern my_bool srv_use_native_aio; -/* Is page compression used */ -extern my_bool srv_compress_pages; - /* Is page compression used only for index pages */ extern my_bool srv_page_compress_index_pages; @@ -259,6 +256,7 @@ extern my_bool srv_use_lz4; /* Number of flush threads */ #define MTFLUSH_MAX_WORKER 64 +#define MTFLUSH_DEFAULT_WORKER 8 extern long srv_mtflush_threads; #ifdef __WIN__ diff --git a/storage/innobase/os/os0file.cc b/storage/innobase/os/os0file.cc index 06c1a8c6ed4..683cd78b901 100644 --- a/storage/innobase/os/os0file.cc +++ b/storage/innobase/os/os0file.cc @@ -6153,6 +6153,7 @@ os_file_trim( ulint len) /*!< in: length of area */ { +#define SECT_SIZE 512 size_t trim_len = UNIV_PAGE_SIZE - len; os_offset_t off = slot->offset + len; @@ -6184,6 +6185,7 @@ os_file_trim( #ifdef __linux__ #if defined(FALLOC_FL_PUNCH_HOLE) && defined (FALLOC_FL_KEEP_SIZE) + trim_len = (trim_len & ~(SECT_SIZE - 1)) + SECT_SIZE; int ret = fallocate(file, FALLOC_FL_PUNCH_HOLE | FALLOC_FL_KEEP_SIZE, off, trim_len); if (ret) { @@ -6252,7 +6254,6 @@ os_file_trim( } #endif -#define SECT_SIZE 512 srv_stats.page_compression_trim_sect512.add((trim_len / SECT_SIZE)); srv_stats.page_compression_trim_sect4096.add((trim_len / (SECT_SIZE*8))); srv_stats.page_compressed_trim_op.inc(); diff --git a/storage/innobase/srv/srv0srv.cc b/storage/innobase/srv/srv0srv.cc index fa1675f7a17..92cfda1c65e 100644 --- a/storage/innobase/srv/srv0srv.cc +++ b/storage/innobase/srv/srv0srv.cc @@ -146,9 +146,6 @@ use simulated aio we build below with threads. Currently we support native aio on windows and linux */ UNIV_INTERN my_bool srv_use_native_aio = TRUE; -/* If this flag is TRUE, then we will use page compression -to the pages */ -UNIV_INTERN my_bool srv_compress_pages = FALSE; /* If this flag is TRUE, then we will use page compression only for index pages */ UNIV_INTERN my_bool srv_page_compress_index_pages = FALSE; @@ -163,7 +160,7 @@ UNIV_INTERN my_bool srv_use_atomic_writes = FALSE; /* If this flag IS TRUE, then we use lz4 to compress/decompress pages */ UNIV_INTERN my_bool srv_use_lz4 = FALSE; /* Number of threads used for multi-threaded flush */ -UNIV_INTERN long srv_mtflush_threads = 0; +UNIV_INTERN long srv_mtflush_threads = MTFLUSH_DEFAULT_WORKER; #ifdef __WIN__ /* Windows native condition variables. We use runtime loading / function diff --git a/storage/innobase/srv/srv0start.cc b/storage/innobase/srv/srv0start.cc index 879b2335720..a469dac8296 100644 --- a/storage/innobase/srv/srv0start.cc +++ b/storage/innobase/srv/srv0start.cc @@ -2593,11 +2593,7 @@ files_checked: if (!srv_read_only_mode) { - if (srv_buf_pool_instances <= MTFLUSH_MAX_WORKER) { - srv_mtflush_threads = srv_buf_pool_instances; - } - /* else we default to 8 worker-threads */ - + /* Start multi-threaded flush threads */ mtflush_ctx = buf_mtflu_handler_init(srv_mtflush_threads, srv_buf_pool_instances); @@ -2607,7 +2603,8 @@ files_checked: (thread_ids + 6 + 32)); #if UNIV_DEBUG - fprintf(stderr, "%s:%d buf-pool-instances:%lu\n", __FILE__, __LINE__, srv_buf_pool_instances); + fprintf(stderr, "InnoDB: Note: %s:%d buf-pool-instances:%lu mtflush_threads %lu\n", + __FILE__, __LINE__, srv_buf_pool_instances, srv_mtflush_threads); #endif os_thread_create(buf_flush_page_cleaner_thread, NULL, NULL); @@ -2879,7 +2876,7 @@ innobase_shutdown_for_mysql(void) buf_mtflu_io_thread_exit(); #ifdef UNIV_DEBUG - fprintf(stderr, "%s:%d os_thread_count:%lu \n", __FUNCTION__, __LINE__, os_thread_count); + fprintf(stderr, "InnoDB: Note: %s:%d os_thread_count:%lu \n", __FUNCTION__, __LINE__, os_thread_count); #endif os_mutex_enter(os_sync_mutex); diff --git a/storage/xtradb/buf/buf0mtflu.cc b/storage/xtradb/buf/buf0mtflu.cc index 5b4d285be21..beb46cc2813 100644 --- a/storage/xtradb/buf/buf0mtflu.cc +++ b/storage/xtradb/buf/buf0mtflu.cc @@ -278,7 +278,7 @@ mtflush_service_io( { wrk_t *work_item = NULL; ulint n_flushed=0; - ib_time_t max_wait_usecs = 5000000; + ib_time_t max_wait_usecs = 50000; mtflush_io->wt_status = WTHR_SIG_WAITING; work_item = (wrk_t *)ib_wqueue_timedwait(mtflush_io->wq, max_wait_usecs); @@ -306,7 +306,8 @@ mtflush_service_io( ut_a(work_item->wi_status == WRK_ITEM_EXIT); work_item->wi_status = WRK_ITEM_EXIT; ib_wqueue_add(mtflush_io->wr_cq, work_item, mtflush_io->wheap); - break; + mtflush_io->wt_status = WTHR_KILL_IT; + return; case MT_WRK_WRITE: work_item->wi_status = WRK_ITEM_START; @@ -352,11 +353,11 @@ DECLARE_THREAD(mtflush_io_thread)( #ifdef UNIV_DEBUG ib_uint64_t stat_universal_num_processed = 0; ib_uint64_t stat_cycle_num_processed = 0; - wrk_t* work_item = mtflush_io[0].work_item; + wrk_t* work_item = mtflush_io[0].work_item; ulint i; #endif - while (srv_shutdown_state != SRV_SHUTDOWN_EXIT_THREADS) { + while (TRUE) { mtflush_service_io(mtflush_io); #ifdef UNIV_DEBUG @@ -371,12 +372,9 @@ DECLARE_THREAD(mtflush_io_thread)( stat_cycle_num_processed); mtflu_print_thread_stat(work_item); #endif - } - - /* This should make sure that all current work items are - processed before threads exit. */ - while (!ib_wqueue_is_empty(mtflush_io->wq)) { - mtflush_service_io(mtflush_io); + if (mtflush_io->wt_status == WTHR_KILL_IT) { + break; + } } os_thread_exit(NULL); @@ -391,16 +389,21 @@ void buf_mtflu_io_thread_exit(void) /*==========================*/ { - ulint i; + long i; thread_sync_t* mtflush_io = mtflush_ctx; ut_a(mtflush_io != NULL); - fprintf(stderr, "signal page_comp_io_threads to exit [%lu]\n", + /* Confirm if the io-thread KILL is in progress, bailout */ + if (mtflush_io->wt_status == WTHR_KILL_IT) { + return; + } + + fprintf(stderr, "signal mtflush_io_threads to exit [%lu]\n", srv_buf_pool_instances); /* Send one exit work item/thread */ - for (i=0; i < srv_buf_pool_instances; i++) { + for (i=0; i < srv_mtflush_threads; i++) { mtflush_io->work_item[i].wr.buf_pool = NULL; mtflush_io->work_item[i].rd.page_pool = NULL; mtflush_io->work_item[i].tsk = MT_WRK_NONE; @@ -413,14 +416,14 @@ buf_mtflu_io_thread_exit(void) /* Wait until all work items on a work queue are processed */ while(!ib_wqueue_is_empty(mtflush_io->wq)) { - /* Wait about 1/2 sec */ - os_thread_sleep(50000); + /* Wait */ + os_thread_sleep(500000); } ut_a(ib_wqueue_is_empty(mtflush_io->wq)); /* Collect all work done items */ - for (i=0; i < srv_buf_pool_instances;) { + for (i=0; i < srv_mtflush_threads;) { wrk_t* work_item; work_item = (wrk_t *)ib_wqueue_timedwait(mtflush_io->wr_cq, 50000); @@ -564,11 +567,13 @@ buf_mtflu_flush_work_items( if((int)done_wi->id_usr == -1 && done_wi->wi_status == WRK_ITEM_SET ) { +#ifdef UNIV_DEBUG fprintf(stderr, "**Set/Unused work_item[%lu] flush_type=%d\n", i, done_wi->wr.flush_type); ut_ad(0); +#endif } n_flushed+= done_wi->n_flushed; diff --git a/storage/xtradb/handler/ha_innodb.cc b/storage/xtradb/handler/ha_innodb.cc index 557872abdf0..f26ad436190 100644 --- a/storage/xtradb/handler/ha_innodb.cc +++ b/storage/xtradb/handler/ha_innodb.cc @@ -10294,14 +10294,6 @@ ha_innobase::check_table_options( /* Check page compression requirements */ if (options->page_compressed) { - if (!srv_compress_pages) { - push_warning( - thd, Sql_condition::WARN_LEVEL_WARN, - HA_WRONG_CREATE_OPTION, - "InnoDB: PAGE_COMPRESSED requires" - "innodb_compress_pages not enabled"); - return "PAGE_COMPRESSED"; - } if (row_format == ROW_TYPE_COMPRESSED) { push_warning( @@ -17942,11 +17934,6 @@ static MYSQL_SYSVAR_BOOL(use_stacktrace, srv_use_stacktrace, "Print stacktrace on long semaphore wait (off by default supported only on linux)", NULL, NULL, FALSE); -static MYSQL_SYSVAR_BOOL(compress_pages, srv_compress_pages, - PLUGIN_VAR_NOCMDARG | PLUGIN_VAR_READONLY, - "Use page compression.", - NULL, NULL, FALSE); - static MYSQL_SYSVAR_LONG(trim_pct, srv_trim_pct, PLUGIN_VAR_OPCMDARG , "How many percent of compressed pages should be trimmed", @@ -17975,6 +17962,15 @@ static MYSQL_SYSVAR_BOOL(use_lz4, srv_use_lz4, NULL, NULL, FALSE); #endif /* HAVE_LZ4 */ +static MYSQL_SYSVAR_LONG(mtflush_threads, srv_mtflush_threads, + PLUGIN_VAR_RQCMDARG, + "Number of multi-threaded flush threads", + NULL, NULL, + MTFLUSH_DEFAULT_WORKER, /* Default setting */ + 1, /* Minimum setting */ + MTFLUSH_MAX_WORKER, /* Max setting */ + 0); + static struct st_mysql_sys_var* innobase_system_variables[]= { MYSQL_SYSVAR(log_block_size), MYSQL_SYSVAR(additional_mem_pool_size), @@ -18165,13 +18161,13 @@ static struct st_mysql_sys_var* innobase_system_variables[]= { MYSQL_SYSVAR(fake_changes), MYSQL_SYSVAR(locking_fake_changes), MYSQL_SYSVAR(use_stacktrace), - MYSQL_SYSVAR(compress_pages), MYSQL_SYSVAR(trim_pct), MYSQL_SYSVAR(compress_index_pages), MYSQL_SYSVAR(use_trim), #ifdef HAVE_LZ4 MYSQL_SYSVAR(use_lz4), #endif + MYSQL_SYSVAR(mtflush_threads), NULL }; diff --git a/storage/xtradb/include/dict0dict.ic b/storage/xtradb/include/dict0dict.ic index d0fbb0d33d2..d37db209beb 100644 --- a/storage/xtradb/include/dict0dict.ic +++ b/storage/xtradb/include/dict0dict.ic @@ -704,7 +704,7 @@ dict_sys_tables_type_validate( if (redundant) { if (zip_ssize || atomic_blobs) { - fprintf(stderr, "InnoDB Error: SYS_TABLES::TYPE=Redundant, zip_ssize %lu atomic_blobs %lu\n", + fprintf(stderr, "InnoDB: Error: SYS_TABLES::TYPE=Redundant, zip_ssize %lu atomic_blobs %lu\n", zip_ssize, atomic_blobs); return(ULINT_UNDEFINED); } @@ -712,7 +712,7 @@ dict_sys_tables_type_validate( /* Make sure there are no bits that we do not know about. */ if (unused) { - fprintf(stderr, "InnoDB Error: SYS_TABLES::TYPE=%lu, unused %lu\n", + fprintf(stderr, "InnoDB: Error: SYS_TABLES::TYPE=%lu, unused %lu\n", type, unused); return(ULINT_UNDEFINED); } @@ -728,7 +728,7 @@ dict_sys_tables_type_validate( } else if (zip_ssize) { /* Antelope does not support COMPRESSED format. */ - fprintf(stderr, "InnoDB Error: SYS_TABLES::TYPE=%lu, zip_ssize %lu\n", + fprintf(stderr, "InnoDB: Error: SYS_TABLES::TYPE=%lu, zip_ssize %lu\n", type, zip_ssize); return(ULINT_UNDEFINED); } @@ -739,14 +739,14 @@ dict_sys_tables_type_validate( should be in N_COLS, but we already know about the low_order_bit and DICT_N_COLS_COMPACT flags. */ if (!atomic_blobs) { - fprintf(stderr, "InnoDB Error: SYS_TABLES::TYPE=%lu, zip_ssize %lu atomic_blobs %lu\n", + fprintf(stderr, "InnoDB: Error: SYS_TABLES::TYPE=%lu, zip_ssize %lu atomic_blobs %lu\n", type, zip_ssize, atomic_blobs); return(ULINT_UNDEFINED); } /* Validate that the number is within allowed range. */ if (zip_ssize > PAGE_ZIP_SSIZE_MAX) { - fprintf(stderr, "InnoDB Error: SYS_TABLES::TYPE=%lu, zip_ssize %lu max %d\n", + fprintf(stderr, "InnoDB: Error: SYS_TABLES::TYPE=%lu, zip_ssize %lu max %d\n", type, zip_ssize, PAGE_ZIP_SSIZE_MAX); return(ULINT_UNDEFINED); } @@ -764,13 +764,20 @@ dict_sys_tables_type_validate( low_order_bit and DICT_N_COLS_COMPACT flags. */ if (!atomic_blobs || !page_compression) { - fprintf(stderr, "InnoDB Error: SYS_TABLES::TYPE=%lu, page_compression %lu page_compression_level %lu\n" + fprintf(stderr, "InnoDB: Error: SYS_TABLES::TYPE=%lu, page_compression %lu page_compression_level %lu\n" "InnoDB: Error: atomic_blobs %lu\n", type, page_compression, page_compression_level, atomic_blobs); return(ULINT_UNDEFINED); } } + /* Validate that the atomic writes number is within allowed range. */ + if (atomic_writes < 0 || atomic_writes > ATOMIC_WRITES_OFF) { + fprintf(stderr, "InnoDB: Error: SYS_TABLES::TYPE=%lu, atomic_writes %lu\n", + type, atomic_writes); + return(ULINT_UNDEFINED); + } + /* Return the validated SYS_TABLES.TYPE. */ return(type); } diff --git a/storage/xtradb/include/fsp0fsp.ic b/storage/xtradb/include/fsp0fsp.ic index bc46967fab0..3563f5ef372 100644 --- a/storage/xtradb/include/fsp0fsp.ic +++ b/storage/xtradb/include/fsp0fsp.ic @@ -67,13 +67,14 @@ fsp_flags_is_valid( ulint page_compression = FSP_FLAGS_GET_PAGE_COMPRESSION(flags); ulint page_compression_level = FSP_FLAGS_GET_PAGE_COMPRESSION_LEVEL(flags); ulint atomic_writes = FSP_FLAGS_GET_ATOMIC_WRITES(flags); - atomic_writes_t awrites = (atomic_writes_t)atomic_writes; DBUG_EXECUTE_IF("fsp_flags_is_valid_failure", return(false);); /* fsp_flags is zero unless atomic_blobs is set. */ /* Make sure there are no bits that we do not know about. */ if (unused != 0 || flags == 1) { + fprintf(stderr, "InnoDB: Error: Tablespace flags %lu corrupted unused %lu\n", + flags, unused); return(false); } else if (post_antelope) { /* The Antelope row formats REDUNDANT and COMPACT did @@ -81,6 +82,8 @@ fsp_flags_is_valid( 4-byte field is zero for Antelope row formats. */ if (!atomic_blobs) { + fprintf(stderr, "InnoDB: Error: Tablespace flags %lu corrupted atomic_blobs %lu\n", + flags, atomic_blobs); return(false); } } @@ -92,10 +95,14 @@ fsp_flags_is_valid( externally stored parts. */ if (post_antelope || zip_ssize != 0) { + fprintf(stderr, "InnoDB: Error: Tablespace flags %lu corrupted zip_ssize %lu atomic_blobs %lu\n", + flags, zip_ssize, atomic_blobs); return(false); } } else if (!post_antelope || zip_ssize > PAGE_ZIP_SSIZE_MAX) { + fprintf(stderr, "InnoDB: Error: Tablespace flags %lu corrupted zip_ssize %lu max %d\n", + flags, zip_ssize, PAGE_ZIP_SSIZE_MAX); return(false); } else if (page_ssize > UNIV_PAGE_SSIZE_MAX) { @@ -103,9 +110,13 @@ fsp_flags_is_valid( be zero for an original 16k page size. Validate the page shift size is within allowed range. */ + fprintf(stderr, "InnoDB: Error: Tablespace flags %lu corrupted page_ssize %lu max %lu\n", + flags, page_ssize, UNIV_PAGE_SSIZE_MAX); return(false); } else if (UNIV_PAGE_SIZE != UNIV_PAGE_SIZE_ORIG && !page_ssize) { + fprintf(stderr, "InnoDB: Error: Tablespace flags %lu corrupted page_ssize %lu max %lu:%d\n", + flags, page_ssize, UNIV_PAGE_SIZE, UNIV_PAGE_SIZE_ORIG); return(false); } @@ -117,13 +128,16 @@ fsp_flags_is_valid( to be set */ if (page_compression_level || page_compression) { if (!page_compression || !atomic_blobs) { + fprintf(stderr, "InnoDB: Error: Tablespace flags %lu corrupted page_compression %lu\n" + "InnoDB: Error: page_compression_level %lu atomic_blobs %lu\n", + flags, page_compression, page_compression_level, atomic_blobs); return(false); } } - if ((awrites == ATOMIC_WRITES_ON || - (awrites == ATOMIC_WRITES_DEFAULT && srv_use_atomic_writes)) - && !atomic_blobs) { + if (atomic_writes < 0 || atomic_writes > ATOMIC_WRITES_OFF) { + fprintf(stderr, "InnoDB: Error: Tablespace flags %lu corrupted atomic_writes %lu\n", + flags, atomic_writes); return (false); } diff --git a/storage/xtradb/include/srv0srv.h b/storage/xtradb/include/srv0srv.h index f7de92d2288..bfb59865841 100644 --- a/storage/xtradb/include/srv0srv.h +++ b/storage/xtradb/include/srv0srv.h @@ -256,9 +256,6 @@ extern ibool srv_use_native_conditions; #endif /* __WIN__ */ #endif /* !UNIV_HOTBACKUP */ -/* Is page compression used */ -extern my_bool srv_compress_pages; - /* Is page compression used only for index pages */ extern my_bool srv_page_compress_index_pages; @@ -279,6 +276,7 @@ extern my_bool srv_use_lz4; /* Number of flush threads */ #define MTFLUSH_MAX_WORKER 64 +#define MTFLUSH_DEFAULT_WORKER 8 extern long srv_mtflush_threads; /** Server undo tablespaces directory, can be absolute path. */ diff --git a/storage/xtradb/os/os0file.cc b/storage/xtradb/os/os0file.cc index 43adf78c63c..d9a5be2b049 100644 --- a/storage/xtradb/os/os0file.cc +++ b/storage/xtradb/os/os0file.cc @@ -6208,6 +6208,7 @@ os_file_trim( ulint len) /*!< in: length of area */ { +#define SECT_SIZE 512 size_t trim_len = UNIV_PAGE_SIZE - len; os_offset_t off = slot->offset + len; @@ -6239,6 +6240,7 @@ os_file_trim( #ifdef __linux__ #if defined(FALLOC_FL_PUNCH_HOLE) && defined (FALLOC_FL_KEEP_SIZE) + trim_len = (trim_len & ~(SECT_SIZE - 1)) + SECT_SIZE; int ret = fallocate(file, FALLOC_FL_PUNCH_HOLE | FALLOC_FL_KEEP_SIZE, off, trim_len); if (ret) { @@ -6307,7 +6309,6 @@ os_file_trim( } #endif -#define SECT_SIZE 512 srv_stats.page_compression_trim_sect512.add((trim_len / SECT_SIZE)); srv_stats.page_compression_trim_sect4096.add((trim_len / (SECT_SIZE*8))); srv_stats.page_compressed_trim_op.inc(); diff --git a/storage/xtradb/srv/srv0srv.cc b/storage/xtradb/srv/srv0srv.cc index 7bd1ef52951..d6801b701ae 100644 --- a/storage/xtradb/srv/srv0srv.cc +++ b/storage/xtradb/srv/srv0srv.cc @@ -161,9 +161,6 @@ use simulated aio we build below with threads. Currently we support native aio on windows and linux */ UNIV_INTERN my_bool srv_use_native_aio = TRUE; -/* If this flag is TRUE, then we will use page compression -to the pages */ -UNIV_INTERN my_bool srv_compress_pages = FALSE; /* If this flag is TRUE, then we will use page compression only for index pages */ UNIV_INTERN my_bool srv_page_compress_index_pages = FALSE; @@ -181,7 +178,7 @@ UNIV_INTERN my_bool srv_use_atomic_writes = FALSE; /* If this flag IS TRUE, then we use lz4 to compress/decompress pages */ UNIV_INTERN my_bool srv_use_lz4 = FALSE; /* Number of threads used for multi-threaded flush */ -UNIV_INTERN long srv_mtflush_threads = 0; +UNIV_INTERN long srv_mtflush_threads = MTFLUSH_DEFAULT_WORKER; #ifdef __WIN__ /* Windows native condition variables. We use runtime loading / function diff --git a/storage/xtradb/srv/srv0start.cc b/storage/xtradb/srv/srv0start.cc index 29afd0d0c98..bb539569e9a 100644 --- a/storage/xtradb/srv/srv0start.cc +++ b/storage/xtradb/srv/srv0start.cc @@ -2718,22 +2718,20 @@ files_checked: } if (!srv_read_only_mode) { - if (srv_buf_pool_instances <= MTFLUSH_MAX_WORKER) { - srv_mtflush_threads = srv_buf_pool_instances; - } + /* Start multi-threaded flush threads */ mtflush_ctx = buf_mtflu_handler_init(srv_mtflush_threads, srv_buf_pool_instances); /* Set up the thread ids */ buf_mtflu_set_thread_ids(srv_mtflush_threads, mtflush_ctx, - (thread_ids + 6 + 32)); + (thread_ids + 6 + SRV_MAX_N_PURGE_THREADS)); #if UNIV_DEBUG - fprintf(stderr, "%s:%d buf-pool-instances:%lu\n", __FILE__, __LINE__, srv_buf_pool_instances); + fprintf(stderr, "InnoDB: Note: %s:%d buf-pool-instances:%lu mtflush_threads %lu\n", + __FILE__, __LINE__, srv_buf_pool_instances, srv_mtflush_threads); #endif - /* JAN: TODO: END */ os_thread_create(buf_flush_page_cleaner_thread, NULL, NULL); } @@ -3011,7 +3009,7 @@ innobase_shutdown_for_mysql(void) buf_mtflu_io_thread_exit(); #ifdef UNIV_DEBUG - fprintf(stderr, "%s:%d os_thread_count:%lu \n", __FUNCTION__, __LINE__, os_thread_count); + fprintf(stderr, "InnoDB: Note: %s:%d os_thread_count:%lu \n", __FUNCTION__, __LINE__, os_thread_count); #endif os_mutex_enter(os_sync_mutex);