MDEV-26110: Do not rely on alignment on static allocation

It is implementation-defined whether alignment requirements
that are larger than std::max_align_t (typically 8 or 16 bytes)
will be honored by the compiler and linker.

It turns out that on IBM AIX, both alignas() and MY_ALIGNED()
only guarantees alignment up to 16 bytes.

For some data structures, specifying alignment to the CPU
cache line size (typically 64 or 128 bytes) is a mere performance
optimization, and we do not really care whether the requested
alignment is guaranteed.

But, for the correct operation of direct I/O, we do require that
the buffers be aligned at a block size boundary.

field_ref_zero: Define as a pointer, not an array.
For innochecksum, we can make this point to unaligned memory;
for anything else, we will allocate an aligned buffer from the heap.
This buffer will be used for overwriting freed data pages when
innodb_immediate_scrub_data_uncompressed=ON. And exactly that code
hit an assertion failure on AIX, in the test innodb.innodb_scrub.

log_sys.checkpoint_buf: Define as a pointer to aligned memory
that is allocated from heap.

log_t::file::write_header_durable(): Reuse log_sys.checkpoint_buf
instead of trying to allocate an aligned buffer from the stack.
This commit is contained in:
Marko Mäkelä 2021-07-22 09:50:20 +03:00
commit 82d5994520
9 changed files with 72 additions and 42 deletions

View file

@ -1,7 +1,7 @@
/*****************************************************************************
Copyright (c) 1995, 2015, Oracle and/or its affiliates. All rights reserved.
Copyright (c) 2019, 2020, MariaDB Corporation.
Copyright (c) 2019, 2021, MariaDB Corporation.
This program is free software; you can redistribute it and/or modify it under
the terms of the GNU General Public License as published by the Free Software
@ -177,11 +177,11 @@ private:
uint64_t m_id;
};
/** A field reference full of zero, for use in assertions and checks,
/** A 64KiB buffer of NUL bytes, for use in assertions and checks,
and dummy default values of instantly dropped columns.
Initially, BLOB field references are set to zero, in
Initially, BLOB field references are set to NUL bytes, in
dtuple_convert_big_rec(). */
extern const byte field_ref_zero[UNIV_PAGE_SIZE_MAX];
extern const byte *field_ref_zero;
#ifndef UNIV_INNOCHECKSUM

View file

@ -617,9 +617,8 @@ public:
/*!< number of currently pending
checkpoint writes */
/** buffer for checkpoint header */
MY_ALIGNED(OS_FILE_LOG_BLOCK_SIZE)
byte checkpoint_buf[OS_FILE_LOG_BLOCK_SIZE];
/** buffer for checkpoint header */
byte *checkpoint_buf;
/* @} */
private: