Skip to content

Commit

Permalink
MDEV-12218 Clean up InnoDB parameter validation
Browse files Browse the repository at this point in the history
Bind more InnoDB parameters directly to MYSQL_SYSVAR and
remove "shadow variables".

innodb_change_buffering: Declare as ENUM, not STRING.

innodb_flush_method: Declare as ENUM, not STRING.

innodb_log_buffer_size: Bind directly to srv_log_buffer_size,
without rounding it to a multiple of innodb_page_size.

LOG_BUFFER_SIZE: Remove.

SysTablespace::normalize_size(): Renamed from normalize().

innodb_init_params(): A new function to initialize and validate
InnoDB startup parameters.

innodb_init(): Renamed from innobase_init(). Invoke innodb_init_params()
before actually trying to start up InnoDB.

srv_start(bool): Renamed from innobase_start_or_create_for_mysql().
Added the input parameter create_new_db.

SRV_ALL_O_DIRECT_FSYNC: Define only for _WIN32.

xb_normalize_init_values(): Merge to innodb_init_param().
  • Loading branch information
dr-m committed Apr 29, 2018
1 parent 9ed2b2b commit 715e4f4
Show file tree
Hide file tree
Showing 46 changed files with 622 additions and 922 deletions.
1 change: 1 addition & 0 deletions extra/mariabackup/backup_mysql.cc
Original file line number Diff line number Diff line change
Expand Up @@ -48,6 +48,7 @@ Place, Suite 330, Boston, MA 02111-1307 USA
#include <limits>
#include "common.h"
#include "xtrabackup.h"
#include "srv0srv.h"
#include "mysql_version.h"
#include "backup_copy.h"
#include "backup_mysql.h"
Expand Down
1 change: 1 addition & 0 deletions extra/mariabackup/changed_page_bitmap.cc
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,7 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA

#include "common.h"
#include "xtrabackup.h"
#include "srv0srv.h"

/* TODO: copy-pasted shared definitions from the XtraDB bitmap write code.
Remove these on the first opportunity, i.e. single-binary XtraBackup. */
Expand Down
1 change: 1 addition & 0 deletions extra/mariabackup/fil_cur.h
Original file line number Diff line number Diff line change
Expand Up @@ -28,6 +28,7 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
#include <my_dir.h>
#include "read_filt.h"
#include "srv0start.h"
#include "srv0srv.h"

struct xb_fil_cur_t {
pfs_os_file_t file; /*!< source file handle */
Expand Down
123 changes: 26 additions & 97 deletions extra/mariabackup/xtrabackup.cc
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@ MariaBackup: hot backup tool for InnoDB
Originally Created 3/3/2009 Yasufumi Kinoshita
Written by Alexey Kopytov, Aleksandr Kuzminsky, Stewart Smith, Vadim Tkachenko,
Yasufumi Kinoshita, Ignacio Nin and Baron Schwartz.
(c) 2017, MariaDB Corporation.
(c) 2017, 2018, MariaDB Corporation.
Portions written by Marko Mäkelä.
This program is free software; you can redistribute it and/or modify
Expand Down Expand Up @@ -223,7 +223,6 @@ long innobase_buffer_pool_awe_mem_mb = 0;
long innobase_file_io_threads = 4;
long innobase_read_io_threads = 4;
long innobase_write_io_threads = 4;
long innobase_log_buffer_size = 1024*1024L;

longlong innobase_page_size = (1LL << 14); /* 16KB */
char* innobase_buffer_pool_filename = NULL;
Expand All @@ -236,9 +235,6 @@ are determined in innobase_init below: */
static char* innobase_ignored_opt;
char* innobase_data_home_dir;
char* innobase_data_file_path;
/* The following has a misleading name: starting from 4.0.5, this also
affects Windows: */
char* innobase_unix_file_flush_method;

my_bool innobase_use_doublewrite;
my_bool innobase_use_large_pages;
Expand Down Expand Up @@ -621,13 +617,9 @@ enum options_xtrabackup
OPT_INNODB_ADAPTIVE_HASH_INDEX,
OPT_INNODB_DOUBLEWRITE,
OPT_INNODB_FILE_PER_TABLE,
OPT_INNODB_FLUSH_LOG_AT_TRX_COMMIT,
OPT_INNODB_FLUSH_METHOD,
OPT_INNODB_LOCKS_UNSAFE_FOR_BINLOG,
OPT_INNODB_LOG_GROUP_HOME_DIR,
OPT_INNODB_MAX_DIRTY_PAGES_PCT,
OPT_INNODB_MAX_PURGE_LAG,
OPT_INNODB_ROLLBACK_ON_TIMEOUT,
OPT_INNODB_STATUS_FILE,
OPT_INNODB_AUTOEXTEND_INCREMENT,
OPT_INNODB_BUFFER_POOL_SIZE,
Expand Down Expand Up @@ -1127,15 +1119,10 @@ struct my_option xb_server_options[] =
(G_PTR*) &innobase_file_per_table, 0, GET_BOOL, NO_ARG,
FALSE, 0, 0, 0, 0, 0},

{"innodb_flush_method", OPT_INNODB_FLUSH_METHOD,
"With which method to flush data.", (G_PTR*) &innobase_unix_file_flush_method,
(G_PTR*) &innobase_unix_file_flush_method, 0, GET_STR, REQUIRED_ARG, 0, 0, 0,
0, 0, 0},

{"innodb_log_buffer_size", OPT_INNODB_LOG_BUFFER_SIZE,
"The size of the buffer which InnoDB uses to write log to the log files on disk.",
(G_PTR*) &innobase_log_buffer_size, (G_PTR*) &innobase_log_buffer_size, 0,
GET_LONG, REQUIRED_ARG, 1024*1024L, 256*1024L, LONG_MAX, 0, 1024, 0},
(G_PTR*) &srv_log_buffer_size, (G_PTR*) &srv_log_buffer_size, 0,
GET_ULONG, REQUIRED_ARG, 1024*1024L, 256*1024L, LONG_MAX, 0, 1024, 0},
{"innodb_log_file_size", OPT_INNODB_LOG_FILE_SIZE,
"Ignored for mysqld option compatibility",
(G_PTR*) &srv_log_file_size, (G_PTR*) &srv_log_file_size, 0,
Expand Down Expand Up @@ -1479,11 +1466,6 @@ xb_get_one_option(int optid,
case OPT_INNODB_LOG_FILE_SIZE:
break;

case OPT_INNODB_FLUSH_METHOD:

ADD_PRINT_PARAM_OPT(innobase_unix_file_flush_method);
break;

case OPT_INNODB_PAGE_SIZE:

ADD_PRINT_PARAM_OPT(innobase_page_size);
Expand Down Expand Up @@ -1587,15 +1569,14 @@ xb_get_one_option(int optid,
return 0;
}

static my_bool
innodb_init_param(void)
static bool innodb_init_param()
{
srv_is_being_started = TRUE;
/* === some variables from mysqld === */
memset((G_PTR) &mysql_tmpdir_list, 0, sizeof(mysql_tmpdir_list));

if (init_tmpdir(&mysql_tmpdir_list, opt_mysql_tmpdir))
exit(EXIT_FAILURE);
return true;
xtrabackup_tmpdir = my_tmpdir(&mysql_tmpdir_list);
/* dummy for initialize all_charsets[] */
get_charset_name(0);
Expand All @@ -1617,7 +1598,7 @@ innodb_init_param(void)
} else {
msg("InnoDB: Error: invalid value of "
"innobase_page_size: %lld", innobase_page_size);
exit(EXIT_FAILURE);
goto error;
}
} else {
srv_page_size_shift = 14;
Expand Down Expand Up @@ -1684,6 +1665,9 @@ innodb_init_param(void)
goto error;
}

srv_sys_space.normalize_size();
srv_lock_table_size = 5 * (srv_buf_pool_size >> srv_page_size_shift);

/* -------------- Log files ---------------------------*/

/* The default dir for log files is the datadir of MySQL */
Expand All @@ -1707,16 +1691,13 @@ innodb_init_param(void)

srv_adaptive_flushing = FALSE;

srv_file_flush_method_str = innobase_unix_file_flush_method;

srv_log_buffer_size = (ulint) innobase_log_buffer_size;

/* We set srv_pool_size here in units of 1 kB. InnoDB internally
changes the value so that it becomes the number of database pages. */

srv_buf_pool_size = (ulint) xtrabackup_use_memory;
srv_buf_pool_chunk_unit = (ulong)srv_buf_pool_size;
srv_buf_pool_instances = 1;
srv_n_page_cleaners = 1;

srv_n_file_io_threads = (ulint) innobase_file_io_threads;
srv_n_read_io_threads = (ulint) innobase_read_io_threads;
Expand All @@ -1732,7 +1713,7 @@ innodb_init_param(void)

srv_locks_unsafe_for_binlog = (ibool) innobase_locks_unsafe_for_binlog;

srv_max_n_open_files = ULINT_UNDEFINED;
srv_max_n_open_files = ULINT_UNDEFINED - 5;
srv_innodb_status = (ibool) innobase_create_status_file;

srv_print_verbose_log = 1;
Expand All @@ -1743,20 +1724,7 @@ innodb_init_param(void)
/* We cannot treat characterset here for now!! */
data_mysql_default_charset_coll = (ulint)default_charset_info->number;

ut_a(DATA_MYSQL_BINARY_CHARSET_COLL == my_charset_bin.number);

//innobase_commit_concurrency_init_default();

/* Since we in this module access directly the fields of a trx
struct, and due to different headers and flags it might happen that
mutex_t has a different size in this module and in InnoDB
modules, we check at run time that the size is the same in
these compilation modules. */

/* On 5.5+ srv_use_native_aio is TRUE by default. It is later reset
if it is not supported by the platform in
innobase_start_or_create_for_mysql(). As we don't call it in xtrabackup,
we have to duplicate checks from that function here. */
ut_ad(DATA_MYSQL_BINARY_CHARSET_COLL == my_charset_bin.number);

#ifdef _WIN32
srv_use_native_aio = TRUE;
Expand Down Expand Up @@ -1789,16 +1757,27 @@ innodb_init_param(void)
? log_block_calc_checksum_crc32
: log_block_calc_checksum_none;

return(FALSE);
#ifdef _WIN32
srv_use_native_aio = TRUE;
#endif
srv_file_flush_method = IF_WIN(SRV_ALL_O_DIRECT_FSYNC, SRV_FSYNC);
return false;

error:
msg("mariabackup: innodb_init_param(): Error occured.\n");
return(TRUE);
return true;
}

static bool innodb_init()
{
dberr_t err = innobase_start_or_create_for_mysql();
bool create_new_db = false;
/* Check if the data files exist or not. */
dberr_t err = srv_sys_space.check_file_spec(&create_new_db, 5U << 20);

if (err == DB_SUCCESS) {
err = srv_start(create_new_db);
}

if (err != DB_SUCCESS) {
msg("mariabackup: innodb_init() returned %d (%s).\n",
err, ut_strerr(err));
Expand Down Expand Up @@ -3583,19 +3562,6 @@ open_or_create_log_file(
return(DB_SUCCESS);
}

/*********************************************************************//**
Normalizes init parameter values to use units we use inside InnoDB.
@return DB_SUCCESS or error code */
static
void
xb_normalize_init_values(void)
/*==========================*/
{
srv_sys_space.normalize();
srv_log_buffer_size >>= srv_page_size_shift;
srv_lock_table_size = 5 * (srv_buf_pool_size >> srv_page_size_shift);
}

/***********************************************************************
Set the open files limit. Based on set_max_open_files().
Expand Down Expand Up @@ -3805,42 +3771,6 @@ xtrabackup_backup_func()
return(false);
}

xb_normalize_init_values();


if (srv_file_flush_method_str == NULL) {
/* These are the default options */
srv_file_flush_method = SRV_FSYNC;
} else if (0 == ut_strcmp(srv_file_flush_method_str, "fsync")) {
srv_file_flush_method = SRV_FSYNC;
} else if (0 == ut_strcmp(srv_file_flush_method_str, "O_DSYNC")) {
srv_file_flush_method = SRV_O_DSYNC;

} else if (0 == ut_strcmp(srv_file_flush_method_str, "O_DIRECT")) {
srv_file_flush_method = SRV_O_DIRECT;
msg("mariabackup: using O_DIRECT\n");
} else if (0 == ut_strcmp(srv_file_flush_method_str, "littlesync")) {
srv_file_flush_method = SRV_LITTLESYNC;
} else if (0 == ut_strcmp(srv_file_flush_method_str, "nosync")) {
srv_file_flush_method = SRV_NOSYNC;
} else if (0 == ut_strcmp(srv_file_flush_method_str, "ALL_O_DIRECT")) {
srv_file_flush_method = SRV_ALL_O_DIRECT_FSYNC;
msg("mariabackup: using ALL_O_DIRECT\n");
} else if (0 == ut_strcmp(srv_file_flush_method_str,
"O_DIRECT_NO_FSYNC")) {
srv_file_flush_method = SRV_O_DIRECT_NO_FSYNC;
msg("mariabackup: using O_DIRECT_NO_FSYNC\n");
} else {
msg("mariabackup: Unrecognized value %s for "
"innodb_flush_method\n", srv_file_flush_method_str);
goto fail;
}

#ifdef _WIN32
srv_file_flush_method = SRV_ALL_O_DIRECT_FSYNC;
srv_use_native_aio = TRUE;
#endif

if (srv_buf_pool_size >= 1000 * 1024 * 1024) {
/* Here we still have srv_pool_size counted
in kilobytes (in 4.0 this was in bytes)
Expand Down Expand Up @@ -5002,7 +4932,6 @@ xtrabackup_prepare_func(char** argv)
goto error_cleanup;
}

xb_normalize_init_values();
sync_check_init();
ut_d(sync_check_enable());
ut_crc32_init();
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -50,9 +50,11 @@ ERROR HY000: Variable 'innodb_change_buffering' is a GLOBAL variable and should
set global innodb_change_buffering=1.1;
ERROR 42000: Incorrect argument type to variable 'innodb_change_buffering'
set global innodb_change_buffering=1;
ERROR 42000: Incorrect argument type to variable 'innodb_change_buffering'
SELECT @@global.innodb_change_buffering;
@@global.innodb_change_buffering
inserts
set global innodb_change_buffering=-2;
ERROR 42000: Incorrect argument type to variable 'innodb_change_buffering'
ERROR 42000: Variable 'innodb_change_buffering' can't be set to the value of '-2'
set global innodb_change_buffering=1e1;
ERROR 42000: Incorrect argument type to variable 'innodb_change_buffering'
set global innodb_change_buffering='some';
Expand Down
24 changes: 12 additions & 12 deletions mysql-test/suite/sys_vars/r/innodb_flush_method_basic.result
Original file line number Diff line number Diff line change
@@ -1,27 +1,27 @@
'#---------------------BS_STVARS_029_01----------------------#'
SELECT COUNT(@@GLOBAL.innodb_flush_method);
COUNT(@@GLOBAL.innodb_flush_method)
0
0 Expected
1
1 Expected
'#---------------------BS_STVARS_029_02----------------------#'
SET @@GLOBAL.innodb_flush_method=1;
ERROR HY000: Variable 'innodb_flush_method' is a read only variable
Expected error 'Read only variable'
SELECT COUNT(@@GLOBAL.innodb_flush_method);
COUNT(@@GLOBAL.innodb_flush_method)
0
0 Expected
1
1 Expected
'#---------------------BS_STVARS_029_03----------------------#'
SELECT @@GLOBAL.innodb_flush_method = VARIABLE_VALUE
FROM INFORMATION_SCHEMA.GLOBAL_VARIABLES
WHERE VARIABLE_NAME='innodb_flush_method';
@@GLOBAL.innodb_flush_method = VARIABLE_VALUE
NULL
1
1 Expected
SELECT COUNT(@@GLOBAL.innodb_flush_method);
COUNT(@@GLOBAL.innodb_flush_method)
0
0 Expected
1
1 Expected
SELECT COUNT(VARIABLE_VALUE)
FROM INFORMATION_SCHEMA.GLOBAL_VARIABLES
WHERE VARIABLE_NAME='innodb_flush_method';
Expand All @@ -31,13 +31,13 @@ COUNT(VARIABLE_VALUE)
'#---------------------BS_STVARS_029_04----------------------#'
SELECT @@innodb_flush_method = @@GLOBAL.innodb_flush_method;
@@innodb_flush_method = @@GLOBAL.innodb_flush_method
NULL
1
1 Expected
'#---------------------BS_STVARS_029_05----------------------#'
SELECT COUNT(@@innodb_flush_method);
COUNT(@@innodb_flush_method)
0
0 Expected
1
1 Expected
SELECT COUNT(@@local.innodb_flush_method);
ERROR HY000: Variable 'innodb_flush_method' is a GLOBAL variable
Expected error 'Variable is a GLOBAL variable'
Expand All @@ -46,8 +46,8 @@ ERROR HY000: Variable 'innodb_flush_method' is a GLOBAL variable
Expected error 'Variable is a GLOBAL variable'
SELECT COUNT(@@GLOBAL.innodb_flush_method);
COUNT(@@GLOBAL.innodb_flush_method)
0
0 Expected
1
1 Expected
SELECT innodb_flush_method = @@SESSION.innodb_flush_method;
ERROR 42S22: Unknown column 'innodb_flush_method' in 'field list'
Expected error 'Readonly variable'
15 changes: 15 additions & 0 deletions mysql-test/suite/sys_vars/r/innodb_flush_method_func.result
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@
call mtr.add_suppression("InnoDB: Failed to set .*DIRECT");
select @@innodb_flush_method;
@@innodb_flush_method
fsync
create table t(a serial) engine=innodb;
FLUSH TABLES;
select @@innodb_flush_method;
@@innodb_flush_method
O_DIRECT_NO_FSYNC
insert into t values(0);
FLUSH TABLES;
select @@innodb_flush_method;
@@innodb_flush_method
fsync
drop table t;
4 changes: 2 additions & 2 deletions mysql-test/suite/sys_vars/r/sysvars_innodb,32bit.rdiff
Original file line number Diff line number Diff line change
Expand Up @@ -293,8 +293,8 @@
GLOBAL_VALUE_ORIGIN CONFIG
DEFAULT_VALUE 16777216
VARIABLE_SCOPE GLOBAL
-VARIABLE_TYPE BIGINT
+VARIABLE_TYPE INT
-VARIABLE_TYPE BIGINT UNSIGNED
+VARIABLE_TYPE INT UNSIGNED
VARIABLE_COMMENT The size of the buffer which InnoDB uses to write log to the log files on disk.
NUMERIC_MIN_VALUE 262144
-NUMERIC_MAX_VALUE 9223372036854775807
Expand Down
Loading

0 comments on commit 715e4f4

Please sign in to comment.