Commit 47cede64 authored by Marko Mäkelä's avatar Marko Mäkelä

MDEV-19543 Deprecate and ignore innodb_log_checksums

The parameter innodb_log_checksums that was introduced in MariaDB 10.2.2
via mysql/mysql-server@af0acedd885eb7103e319f79d25fda7386ef1506
does not make much sense. The original motivation of introducing this
parameter (initially called innodb_log_checksum_algorithm in
mysql/mysql-server@22ba38218e1d76c24f69b5a5595ad3bf5933acb0)
was that the InnoDB redo log used the slow and insecure innodb algorithm.
With hardware or SIMD accelerated CRC-32C, there should be no reason to
allow checksums to be disabled on the redo log.

The parameter innodb_encrypt_log already implies innodb_log_checksums=ON.

Let us deprecate the parameter innodb_log_checksums and always compute
redo log checksums, even if innodb_log_checksums=OFF is specified.

An upgrade from MariaDB 10.2.2 or later will only be possible after
using the default value innodb_log_checksums=ON. If the non-default
value innodb_log_checksums=OFF was in effect when the server was shut down,
a log block checksum mismatch will be reported and the upgraded server
will fail to start up.
parent 3eef9f21
...@@ -1367,11 +1367,6 @@ struct my_option xb_server_options[] = ...@@ -1367,11 +1367,6 @@ struct my_option xb_server_options[] =
&xb_plugin_dir, &xb_plugin_dir, &xb_plugin_dir, &xb_plugin_dir,
0, GET_STR, REQUIRED_ARG, 0, 0, 0, 0, 0, 0 }, 0, GET_STR, REQUIRED_ARG, 0, 0, 0, 0, 0, 0 },
{"innodb-log-checksums", OPT_INNODB_LOG_CHECKSUMS,
"Whether to require checksums for InnoDB redo log blocks",
&innodb_log_checksums, &innodb_log_checksums,
0, GET_BOOL, REQUIRED_ARG, 1, 0, 0, 0, 0, 0 },
{"open_files_limit", OPT_OPEN_FILES_LIMIT, "the maximum number of file " {"open_files_limit", OPT_OPEN_FILES_LIMIT, "the maximum number of file "
"descriptors to reserve with setrlimit().", "descriptors to reserve with setrlimit().",
(G_PTR*) &xb_open_files_limit, (G_PTR*) &xb_open_files_limit, 0, GET_ULONG, (G_PTR*) &xb_open_files_limit, (G_PTR*) &xb_open_files_limit, 0, GET_ULONG,
...@@ -1959,10 +1954,6 @@ static bool innodb_init_param() ...@@ -1959,10 +1954,6 @@ static bool innodb_init_param()
srv_undo_dir = (char*) "."; srv_undo_dir = (char*) ".";
} }
log_checksum_algorithm_ptr = innodb_log_checksums || srv_encrypt_log
? log_block_calc_checksum_crc32
: log_block_calc_checksum_none;
#ifdef _WIN32 #ifdef _WIN32
srv_use_native_aio = TRUE; srv_use_native_aio = TRUE;
#endif #endif
......
...@@ -7,7 +7,7 @@ ...@@ -7,7 +7,7 @@
# #
SET GLOBAL innodb_log_checksums=0; SET GLOBAL innodb_log_checksums=0;
Warnings: Warnings:
Warning 138 innodb_encrypt_log implies innodb_log_checksums Warning 138 The parameter innodb_log_checksums is deprecated and has no effect.
SELECT @@global.innodb_log_checksums; SELECT @@global.innodb_log_checksums;
@@global.innodb_log_checksums @@global.innodb_log_checksums
1 1
......
...@@ -28,15 +28,23 @@ SELECT @@global.innodb_log_checksums; ...@@ -28,15 +28,23 @@ SELECT @@global.innodb_log_checksums;
@@global.innodb_log_checksums @@global.innodb_log_checksums
1 1
SET GLOBAL innodb_log_checksums = OFF; SET GLOBAL innodb_log_checksums = OFF;
Warnings:
Warning 138 The parameter innodb_log_checksums is deprecated and has no effect.
SELECT @@global.innodb_log_checksums; SELECT @@global.innodb_log_checksums;
@@global.innodb_log_checksums @@global.innodb_log_checksums
0 1
SET GLOBAL innodb_log_checksums = default; SET GLOBAL innodb_log_checksums = default;
Warnings:
Warning 138 The parameter innodb_log_checksums is deprecated and has no effect.
SET GLOBAL innodb_log_checksums = ON; SET GLOBAL innodb_log_checksums = ON;
Warnings:
Warning 138 The parameter innodb_log_checksums is deprecated and has no effect.
SELECT @@global.innodb_log_checksums; SELECT @@global.innodb_log_checksums;
@@global.innodb_log_checksums @@global.innodb_log_checksums
1 1
SET GLOBAL innodb_log_checksums = @orig; SET GLOBAL innodb_log_checksums = @orig;
Warnings:
Warning 138 The parameter innodb_log_checksums is deprecated and has no effect.
SELECT @@global.innodb_log_checksums; SELECT @@global.innodb_log_checksums;
@@global.innodb_log_checksums @@global.innodb_log_checksums
1 1
...@@ -1401,7 +1401,7 @@ GLOBAL_VALUE_ORIGIN COMPILE-TIME ...@@ -1401,7 +1401,7 @@ GLOBAL_VALUE_ORIGIN COMPILE-TIME
DEFAULT_VALUE ON DEFAULT_VALUE ON
VARIABLE_SCOPE GLOBAL VARIABLE_SCOPE GLOBAL
VARIABLE_TYPE BOOLEAN VARIABLE_TYPE BOOLEAN
VARIABLE_COMMENT Whether to compute and require checksums for InnoDB redo log blocks VARIABLE_COMMENT Deprecated parameter with no effect.
NUMERIC_MIN_VALUE NULL NUMERIC_MIN_VALUE NULL
NUMERIC_MAX_VALUE NULL NUMERIC_MAX_VALUE NULL
NUMERIC_BLOCK_SIZE NULL NUMERIC_BLOCK_SIZE NULL
......
...@@ -3555,46 +3555,6 @@ static int innodb_init_abort() ...@@ -3555,46 +3555,6 @@ static int innodb_init_abort()
DBUG_RETURN(1); DBUG_RETURN(1);
} }
/** Update log_checksum_algorithm_ptr with a pointer to the function
corresponding to whether checksums are enabled.
@param[in,out] thd client session, or NULL if at startup
@param[in] check whether redo log block checksums are enabled
@return whether redo log block checksums are enabled */
static inline
bool
innodb_log_checksums_func_update(THD* thd, bool check)
{
static const char msg[] = "innodb_encrypt_log implies"
" innodb_log_checksums";
ut_ad(!thd == !srv_was_started);
if (!check) {
check = srv_encrypt_log;
if (!check) {
} else if (thd) {
push_warning_printf(thd, Sql_condition::WARN_LEVEL_WARN,
HA_ERR_UNSUPPORTED, msg);
} else {
sql_print_warning(msg);
}
}
if (thd) {
log_mutex_enter();
log_checksum_algorithm_ptr = check
? log_block_calc_checksum_crc32
: log_block_calc_checksum_none;
log_mutex_exit();
} else {
log_checksum_algorithm_ptr = check
? log_block_calc_checksum_crc32
: log_block_calc_checksum_none;
}
return(check);
}
/****************************************************************//** /****************************************************************//**
Gives the file extension of an InnoDB single-table tablespace. */ Gives the file extension of an InnoDB single-table tablespace. */
static const char* ha_innobase_exts[] = { static const char* ha_innobase_exts[] = {
...@@ -3692,6 +3652,12 @@ static void innodb_buffer_pool_size_init() ...@@ -3692,6 +3652,12 @@ static void innodb_buffer_pool_size_init()
innobase_buffer_pool_size = srv_buf_pool_size; innobase_buffer_pool_size = srv_buf_pool_size;
} }
/** Deprecated parameter with no effect */
static my_bool innodb_log_checksums;
/** Deprecation message for innodb_log_checksums */
static const char* innodb_log_checksums_deprecated
= "The parameter innodb_log_checksums is deprecated and has no effect.";
/** Initialize, validate and normalize the InnoDB startup parameters. /** Initialize, validate and normalize the InnoDB startup parameters.
@return failure code @return failure code
@retval 0 on success @retval 0 on success
...@@ -4006,8 +3972,10 @@ static int innodb_init_params() ...@@ -4006,8 +3972,10 @@ static int innodb_init_params()
srv_buf_pool_size = ulint(innobase_buffer_pool_size); srv_buf_pool_size = ulint(innobase_buffer_pool_size);
innodb_log_checksums = innodb_log_checksums_func_update( if (!innodb_log_checksums) {
NULL, innodb_log_checksums); sql_print_warning(innodb_log_checksums_deprecated);
innodb_log_checksums = TRUE;
}
row_rollback_on_timeout = (ibool) innobase_rollback_on_timeout; row_rollback_on_timeout = (ibool) innobase_rollback_on_timeout;
...@@ -18586,17 +18554,14 @@ innodb_encrypt_tables_update(THD*, st_mysql_sys_var*, void*, const void* save) ...@@ -18586,17 +18554,14 @@ innodb_encrypt_tables_update(THD*, st_mysql_sys_var*, void*, const void* save)
fil_crypt_set_encrypt_tables(*static_cast<const ulong*>(save)); fil_crypt_set_encrypt_tables(*static_cast<const ulong*>(save));
} }
/** Update the innodb_log_checksums parameter. /** Issue a deprecation warning for SET GLOBAL innodb_log_checksums.
@param[in,out] thd client connection @param[in,out] thd client connection */
@param[out] var_ptr current value static void
@param[in] save immediate result from check function */ innodb_log_checksums_warn(THD* thd, st_mysql_sys_var*, void*, const void*)
static
void
innodb_log_checksums_update(THD* thd, st_mysql_sys_var*, void* var_ptr,
const void* save)
{ {
*static_cast<my_bool*>(var_ptr) = innodb_log_checksums_func_update( push_warning_printf(thd, Sql_condition::WARN_LEVEL_WARN,
thd, *static_cast<const my_bool*>(save)); HA_ERR_UNSUPPORTED,
innodb_log_checksums_deprecated);
} }
static SHOW_VAR innodb_status_variables_export[]= { static SHOW_VAR innodb_status_variables_export[]= {
...@@ -18795,8 +18760,8 @@ static MYSQL_SYSVAR_ENUM(checksum_algorithm, srv_checksum_algorithm, ...@@ -18795,8 +18760,8 @@ static MYSQL_SYSVAR_ENUM(checksum_algorithm, srv_checksum_algorithm,
static MYSQL_SYSVAR_BOOL(log_checksums, innodb_log_checksums, static MYSQL_SYSVAR_BOOL(log_checksums, innodb_log_checksums,
PLUGIN_VAR_RQCMDARG, PLUGIN_VAR_RQCMDARG,
"Whether to compute and require checksums for InnoDB redo log blocks", "Deprecated parameter with no effect.",
NULL, innodb_log_checksums_update, TRUE); NULL, innodb_log_checksums_warn, TRUE);
static MYSQL_SYSVAR_STR(data_home_dir, innobase_data_home_dir, static MYSQL_SYSVAR_STR(data_home_dir, innobase_data_home_dir,
PLUGIN_VAR_READONLY, PLUGIN_VAR_READONLY,
......
...@@ -54,10 +54,6 @@ step which modifies the database, is started */ ...@@ -54,10 +54,6 @@ step which modifies the database, is started */
typedef ulint (*log_checksum_func_t)(const byte* log_block); typedef ulint (*log_checksum_func_t)(const byte* log_block);
/** Pointer to the log checksum calculation function. Protected with
log_sys.mutex. */
extern log_checksum_func_t log_checksum_algorithm_ptr;
/** Append a string to the log. /** Append a string to the log.
@param[in] str string @param[in] str string
@param[in] len string length @param[in] len string length
...@@ -261,28 +257,10 @@ log_block_set_data_len( ...@@ -261,28 +257,10 @@ log_block_set_data_len(
/*===================*/ /*===================*/
byte* log_block, /*!< in/out: log block */ byte* log_block, /*!< in/out: log block */
ulint len); /*!< in: data length */ ulint len); /*!< in: data length */
/************************************************************//** /** Calculate the CRC-32C checksum of a log block.
Calculates the checksum for a log block.
@return checksum */
UNIV_INLINE
ulint
log_block_calc_checksum(
/*====================*/
const byte* block); /*!< in: log block */
/** Calculates the checksum for a log block using the CRC32 algorithm.
@param[in] block log block @param[in] block log block
@return checksum */ @return checksum */
UNIV_INLINE inline ulint log_block_calc_checksum_crc32(const byte* block);
ulint
log_block_calc_checksum_crc32(
const byte* block);
/** Calculates the checksum for a log block using the "no-op" algorithm.
@return the calculated checksum value */
UNIV_INLINE
ulint
log_block_calc_checksum_none(const byte*);
/************************************************************//** /************************************************************//**
Gets a log block checksum field value. Gets a log block checksum field value.
...@@ -360,9 +338,6 @@ void ...@@ -360,9 +338,6 @@ void
log_refresh_stats(void); log_refresh_stats(void);
/*===================*/ /*===================*/
/** Whether to generate and require checksums on the redo log pages */
extern my_bool innodb_log_checksums;
/* Values used as flags */ /* Values used as flags */
#define LOG_FLUSH 7652559 #define LOG_FLUSH 7652559
#define LOG_CHECKPOINT 78656949 #define LOG_CHECKPOINT 78656949
......
...@@ -188,18 +188,6 @@ log_block_convert_lsn_to_no( ...@@ -188,18 +188,6 @@ log_block_convert_lsn_to_no(
return(((ulint) (lsn / OS_FILE_LOG_BLOCK_SIZE) & 0x3FFFFFFFUL) + 1); return(((ulint) (lsn / OS_FILE_LOG_BLOCK_SIZE) & 0x3FFFFFFFUL) + 1);
} }
/************************************************************//**
Calculates the checksum for a log block.
@return checksum */
UNIV_INLINE
ulint
log_block_calc_checksum(
/*====================*/
const byte* block) /*!< in: log block */
{
return(log_checksum_algorithm_ptr(block));
}
/** Calculate the checksum for a log block using the pre-5.7.9 algorithm. /** Calculate the checksum for a log block using the pre-5.7.9 algorithm.
@param[in] block log block @param[in] block log block
@return checksum */ @return checksum */
...@@ -229,26 +217,14 @@ log_block_calc_checksum_format_0( ...@@ -229,26 +217,14 @@ log_block_calc_checksum_format_0(
return(sum); return(sum);
} }
/** Calculate the checksum for a log block using the MySQL 5.7 algorithm. /** Calculate the CRC-32C checksum of a log block.
@param[in] block log block @param[in] block log block
@return checksum */ @return checksum */
UNIV_INLINE inline ulint log_block_calc_checksum_crc32(const byte* block)
ulint
log_block_calc_checksum_crc32(
const byte* block)
{ {
return ut_crc32(block, OS_FILE_LOG_BLOCK_SIZE - LOG_BLOCK_CHECKSUM); return ut_crc32(block, OS_FILE_LOG_BLOCK_SIZE - LOG_BLOCK_CHECKSUM);
} }
/** Calculates the checksum for a log block using the "no-op" algorithm.
@return checksum */
UNIV_INLINE
ulint
log_block_calc_checksum_none(const byte*)
{
return(LOG_NO_CHECKSUM_MAGIC);
}
/************************************************************//** /************************************************************//**
Gets a log block checksum field value. Gets a log block checksum field value.
@return checksum */ @return checksum */
......
...@@ -83,12 +83,6 @@ reduce the size of the log. ...@@ -83,12 +83,6 @@ reduce the size of the log.
/** Redo log system */ /** Redo log system */
log_t log_sys; log_t log_sys;
/** Whether to generate and require checksums on the redo log pages */
my_bool innodb_log_checksums;
/** Pointer to the log checksum calculation function */
log_checksum_func_t log_checksum_algorithm_ptr;
/* Next log block number to do dummy record filling if no log records written /* Next log block number to do dummy record filling if no log records written
for a while */ for a while */
static ulint next_lbn_to_pad = 0; static ulint next_lbn_to_pad = 0;
...@@ -669,6 +663,12 @@ void log_t::files::create(ulint n_files) ...@@ -669,6 +663,12 @@ void log_t::files::create(ulint n_files)
lsn_offset= LOG_FILE_HDR_SIZE; lsn_offset= LOG_FILE_HDR_SIZE;
} }
/** Update the log block checksum. */
inline void log_block_store_checksum(byte* block)
{
log_block_set_checksum(block, log_block_calc_checksum_crc32(block));
}
/******************************************************//** /******************************************************//**
Writes a log file header to a log file space. */ Writes a log file header to a log file space. */
static static
...@@ -698,7 +698,7 @@ log_file_header_flush( ...@@ -698,7 +698,7 @@ log_file_header_flush(
LOG_HEADER_CREATOR_CURRENT); LOG_HEADER_CREATOR_CURRENT);
ut_ad(LOG_HEADER_CREATOR_END - LOG_HEADER_CREATOR ut_ad(LOG_HEADER_CREATOR_END - LOG_HEADER_CREATOR
>= sizeof LOG_HEADER_CREATOR_CURRENT); >= sizeof LOG_HEADER_CREATOR_CURRENT);
log_block_set_checksum(buf, log_block_calc_checksum_crc32(buf)); log_block_store_checksum(buf);
dest_offset = nth_file * log_sys.log.file_size; dest_offset = nth_file * log_sys.log.file_size;
...@@ -723,19 +723,6 @@ log_file_header_flush( ...@@ -723,19 +723,6 @@ log_file_header_flush(
srv_stats.os_log_pending_writes.dec(); srv_stats.os_log_pending_writes.dec();
} }
/******************************************************//**
Stores a 4-byte checksum to the trailer checksum field of a log block
before writing it to a log file. This checksum is used in recovery to
check the consistency of a log block. */
static
void
log_block_store_checksum(
/*=====================*/
byte* block) /*!< in/out: pointer to a log block */
{
log_block_set_checksum(block, log_block_calc_checksum(block));
}
/******************************************************//** /******************************************************//**
Writes a buffer to a log file. */ Writes a buffer to a log file. */
static static
...@@ -1315,7 +1302,7 @@ log_group_checkpoint(lsn_t end_lsn) ...@@ -1315,7 +1302,7 @@ log_group_checkpoint(lsn_t end_lsn)
srv_log_buffer_size); srv_log_buffer_size);
mach_write_to_8(buf + LOG_CHECKPOINT_END_LSN, end_lsn); mach_write_to_8(buf + LOG_CHECKPOINT_END_LSN, end_lsn);
log_block_set_checksum(buf, log_block_calc_checksum_crc32(buf)); log_block_store_checksum(buf);
MONITOR_INC(MONITOR_PENDING_CHECKPOINT_WRITE); MONITOR_INC(MONITOR_PENDING_CHECKPOINT_WRITE);
......
...@@ -959,7 +959,6 @@ bool log_t::files::read_log_seg(lsn_t* start_lsn, lsn_t end_lsn) ...@@ -959,7 +959,6 @@ bool log_t::files::read_log_seg(lsn_t* start_lsn, lsn_t end_lsn)
break; break;
} }
if (innodb_log_checksums || is_encrypted()) {
ulint crc = log_block_calc_checksum_crc32(buf); ulint crc = log_block_calc_checksum_crc32(buf);
ulint cksum = log_block_get_checksum(buf); ulint cksum = log_block_get_checksum(buf);
...@@ -986,7 +985,6 @@ bool log_t::files::read_log_seg(lsn_t* start_lsn, lsn_t end_lsn) ...@@ -986,7 +985,6 @@ bool log_t::files::read_log_seg(lsn_t* start_lsn, lsn_t end_lsn)
LOG_DECRYPT)) { LOG_DECRYPT)) {
goto fail; goto fail;
} }
}
ulint dl = log_block_get_data_len(buf); ulint dl = log_block_get_data_len(buf);
if (dl < LOG_BLOCK_HDR_SIZE if (dl < LOG_BLOCK_HDR_SIZE
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment