Commit 3c21eccb authored by Marko Mäkelä's avatar Marko Mäkelä

MDEV-15764 InnoDB may write uninitialized garbage to redo log

log_write_up_to(): Erase the end of the current log block.
Simplify the computation of pad_size.

log_buffer_switch(): Evaluate a condition only once.
parent d9c5a466
...@@ -1085,17 +1085,17 @@ log_buffer_switch() ...@@ -1085,17 +1085,17 @@ log_buffer_switch()
OS_FILE_LOG_BLOCK_SIZE); OS_FILE_LOG_BLOCK_SIZE);
if (log_sys->first_in_use) { if (log_sys->first_in_use) {
log_sys->first_in_use = false;
ut_ad(log_sys->buf == ut_align(log_sys->buf_ptr, ut_ad(log_sys->buf == ut_align(log_sys->buf_ptr,
OS_FILE_LOG_BLOCK_SIZE)); OS_FILE_LOG_BLOCK_SIZE));
log_sys->buf += log_sys->buf_size; log_sys->buf += log_sys->buf_size;
} else { } else {
log_sys->first_in_use = true;
log_sys->buf -= log_sys->buf_size; log_sys->buf -= log_sys->buf_size;
ut_ad(log_sys->buf == ut_align(log_sys->buf_ptr, ut_ad(log_sys->buf == ut_align(log_sys->buf_ptr,
OS_FILE_LOG_BLOCK_SIZE)); OS_FILE_LOG_BLOCK_SIZE));
} }
log_sys->first_in_use = !log_sys->first_in_use;
/* Copy the last block to new buf */ /* Copy the last block to new buf */
ut_memcpy(log_sys->buf, ut_memcpy(log_sys->buf,
old_buf + area_end - OS_FILE_LOG_BLOCK_SIZE, old_buf + area_end - OS_FILE_LOG_BLOCK_SIZE,
...@@ -1235,6 +1235,9 @@ log_write_up_to( ...@@ -1235,6 +1235,9 @@ log_write_up_to(
log_group_set_fields(&log_sys->log, log_sys->write_lsn); log_group_set_fields(&log_sys->log, log_sys->write_lsn);
log_mutex_exit(); log_mutex_exit();
/* Erase the end of the last log block. */
memset(write_buf + end_offset, 0, ~end_offset & OS_FILE_LOG_BLOCK_SIZE);
/* Calculate pad_size if needed. */ /* Calculate pad_size if needed. */
pad_size = 0; pad_size = 0;
if (write_ahead_size > OS_FILE_LOG_BLOCK_SIZE) { if (write_ahead_size > OS_FILE_LOG_BLOCK_SIZE) {
...@@ -1251,12 +1254,9 @@ log_write_up_to( ...@@ -1251,12 +1254,9 @@ log_write_up_to(
/* The first block in the unit was initialized /* The first block in the unit was initialized
after the last writing. after the last writing.
Needs to be written padded data once. */ Needs to be written padded data once. */
pad_size = write_ahead_size - end_offset_in_unit; pad_size = std::min(
ulint(write_ahead_size) - end_offset_in_unit,
if (area_end + pad_size > log_sys->buf_size) { log_sys->buf_size - area_end);
pad_size = log_sys->buf_size - area_end;
}
::memset(write_buf + area_end, 0, pad_size); ::memset(write_buf + area_end, 0, pad_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