diff options
author | Sachin Setiya <sachinsetia1001@gmail.com> | 2017-01-10 10:08:04 +0530 |
---|---|---|
committer | Sachin Setiya <sachinsetia1001@gmail.com> | 2017-01-27 17:09:35 +0530 |
commit | 06853d45de66cf825e7c6aaf3190c5bf6715625e (patch) | |
tree | 3e9c8ed78d5ffb255e72ad3c882dcd2f79b41dba | |
parent | b72b9bead74601b6b0ee166e8b55f9417ad0faac (diff) | |
download | mariadb-git-bb-10.0-gal-sachin.tar.gz |
MDEV-4774 Strangeness with max_binlog_stmt_cache_size Settingsbb-10.0-gal-sachin
Problem:- When setting max_binlog_stmt_cache_size=18446744073709547520
from either command line or .cnf file, server fails to start.
Solution:- Added one more function eval_num_suffix_ull , which uses
strtoull to get unsigned ulonglong from string. And getopt_ull calls this
function instead of eval_num_suffix. Also changed previous eval_num_suffix to
eval_num_suffix_ll to remain consistent.
4 files changed, 107 insertions, 12 deletions
diff --git a/mysql-test/suite/binlog/r/binlog_max_binlog_stmt_cache_size.result b/mysql-test/suite/binlog/r/binlog_max_binlog_stmt_cache_size.result new file mode 100644 index 00000000000..6659148f24a --- /dev/null +++ b/mysql-test/suite/binlog/r/binlog_max_binlog_stmt_cache_size.result @@ -0,0 +1,16 @@ +select @@max_binlog_stmt_cache_size; +@@max_binlog_stmt_cache_size +18446744073709547520 +SET @cache_size= @@max_binlog_stmt_cache_size; +SET @max_uint64= 18446744073709551615; +SET @max_uint32= 4294967295; +SET @max_absolute_value = if (@max_uint32 < @cache_size, @max_uint64, @max_uint32); +set global max_binlog_stmt_cache_size= @cache_size+1; +select @@max_binlog_stmt_cache_size; +@@max_binlog_stmt_cache_size +18446744073709547520 +set global max_binlog_stmt_cache_size= @cache_size-1; +select @@max_binlog_stmt_cache_size = @cache_size-4096; +@@max_binlog_stmt_cache_size = @cache_size-4096 +1 +set @@global.max_binlog_stmt_cache_size= @cache_size; diff --git a/mysql-test/suite/binlog/t/binlog_max_binlog_stmt_cache_size.opt b/mysql-test/suite/binlog/t/binlog_max_binlog_stmt_cache_size.opt new file mode 100644 index 00000000000..c52ef14d5d0 --- /dev/null +++ b/mysql-test/suite/binlog/t/binlog_max_binlog_stmt_cache_size.opt @@ -0,0 +1 @@ +--max_binlog_stmt_cache_size=18446744073709547520 diff --git a/mysql-test/suite/binlog/t/binlog_max_binlog_stmt_cache_size.test b/mysql-test/suite/binlog/t/binlog_max_binlog_stmt_cache_size.test new file mode 100644 index 00000000000..10769efb9f9 --- /dev/null +++ b/mysql-test/suite/binlog/t/binlog_max_binlog_stmt_cache_size.test @@ -0,0 +1,30 @@ +source include/have_log_bin.inc; +select @@max_binlog_stmt_cache_size; + +--replace_result 18446744073709547520 max_binlog_stmt_cache_size 4294963200 max_binlog_stmt_cache_size +--disable_warnings +SET @cache_size= @@max_binlog_stmt_cache_size; +SET @max_uint64= 18446744073709551615; +SET @max_uint32= 4294967295; +SET @max_absolute_value = if (@max_uint32 < @cache_size, @max_uint64, @max_uint32); + +set global max_binlog_stmt_cache_size= @cache_size+1; +select @@max_binlog_stmt_cache_size; + +set global max_binlog_stmt_cache_size= @cache_size-1; +select @@max_binlog_stmt_cache_size = @cache_size-4096; + + +#this can be commented out if IF(cond, expr,expr) bug is solved +#Select @max_absolute_value; +#set global max_binlog_stmt_cache_size= @max_absolute_value-4096; +#select @@max_binlog_stmt_cache_size; + +#set global max_binlog_stmt_cache_size= @max_absolute_value -1; +#select @@max_binlog_stmt_cache_size; + +#--error ER_WRONG_TYPE_FOR_VAR +#set global max_binlog_stmt_cache_size= @max_absolute_value +1; +#select @@max_binlog_stmt_cache_size; + +set @@global.max_binlog_stmt_cache_size= @cache_size; diff --git a/mysys/my_getopt.c b/mysys/my_getopt.c index 2a4557118b0..e68a08ee735 100644 --- a/mysys/my_getopt.c +++ b/mysys/my_getopt.c @@ -895,15 +895,39 @@ my_bool getopt_compare_strings(register const char *s, register const char *t, /* function: eval_num_suffix + Transforms suffix like k/m/g to their real value. +*/ + +static inline long eval_num_suffix(char *suffix, int *error) +{ + long num= 1; + if (*suffix == 'k' || *suffix == 'K') + num*= 1024L; + else if (*suffix == 'm' || *suffix == 'M') + num*= 1024L * 1024L; + else if (*suffix == 'g' || *suffix == 'G') + num*= 1024L * 1024L * 1024L; + else if (*suffix) + { + *error= 1; + return 0; + } + return num; +} + +/* + function: eval_num_suffix_ll + Transforms a number with a suffix to real number. Suffix can be k|K for kilo, m|M for mega or g|G for giga. */ -static longlong eval_num_suffix(char *argument, int *error, char *option_name) +static longlong eval_num_suffix_ll(char *argument, + int *error, char *option_name) { char *endchar; longlong num; - DBUG_ENTER("eval_num_suffix"); + DBUG_ENTER("eval_num_suffix_ll"); *error= 0; @@ -916,23 +940,47 @@ static longlong eval_num_suffix(char *argument, int *error, char *option_name) *error= 1; DBUG_RETURN(0); } - if (*endchar == 'k' || *endchar == 'K') - num*= 1024L; - else if (*endchar == 'm' || *endchar == 'M') - num*= 1024L * 1024L; - else if (*endchar == 'g' || *endchar == 'G') - num*= 1024L * 1024L * 1024L; - else if (*endchar) - { + num*= eval_num_suffix(endchar, error); + if (*error) fprintf(stderr, "Unknown suffix '%c' used for variable '%s' (value '%s')\n", *endchar, option_name, argument); + DBUG_RETURN(num); +} + +/* + function: eval_num_suffix_ull + + Transforms a number with a suffix to positive Integer. Suffix can + be k|K for kilo, m|M for mega or g|G for giga. +*/ + +static ulonglong eval_num_suffix_ull(char *argument, + int *error, char *option_name) +{ + char *endchar; + ulonglong num; + DBUG_ENTER("eval_num_suffix_ull"); + + *error= 0; + errno= 0; + num= strtoull(argument, &endchar, 10); + if (errno == ERANGE) + { + my_getopt_error_reporter(ERROR_LEVEL, + "Incorrect integer value: '%s'", argument); *error= 1; DBUG_RETURN(0); } + num*= eval_num_suffix(endchar, error); + if (*error) + fprintf(stderr, + "Unknown suffix '%c' used for variable '%s' (value '%s')\n", + *endchar, option_name, argument); DBUG_RETURN(num); } + /* function: getopt_ll @@ -946,7 +994,7 @@ static longlong eval_num_suffix(char *argument, int *error, char *option_name) static longlong getopt_ll(char *arg, const struct my_option *optp, int *err) { - longlong num=eval_num_suffix(arg, err, (char*) optp->name); + longlong num=eval_num_suffix_ll(arg, err, (char*) optp->name); return getopt_ll_limit_value(num, optp, NULL); } @@ -1023,7 +1071,7 @@ longlong getopt_ll_limit_value(longlong num, const struct my_option *optp, static ulonglong getopt_ull(char *arg, const struct my_option *optp, int *err) { - ulonglong num= eval_num_suffix(arg, err, (char*) optp->name); + ulonglong num= eval_num_suffix_ull(arg, err, (char*) optp->name); return getopt_ull_limit_value(num, optp, NULL); } |