Commit 58252fff authored by Marko Mäkelä's avatar Marko Mäkelä

MDEV-26040 os_file_set_size() may not work on O_DIRECT files

os_file_set_size(): Trim the current size down to the file system
block size, to obey the constraints for unbuffered I/O.
parent 8147d2e6
......@@ -5420,6 +5420,8 @@ os_file_set_size(
fallback:
#else
struct stat statbuf;
if (is_sparse) {
bool success = !ftruncate(file, size);
if (!success) {
......@@ -5433,10 +5435,17 @@ os_file_set_size(
# ifdef HAVE_POSIX_FALLOCATE
int err;
do {
os_offset_t current_size = os_file_get_size(file);
err = current_size >= size
? 0 : posix_fallocate(file, current_size,
if (fstat(file, &statbuf)) {
err = errno;
} else {
os_offset_t current_size = statbuf.st_size;
if (current_size >= size) {
return true;
}
current_size &= ~os_offset_t(statbuf.st_blksize - 1);
err = posix_fallocate(file, current_size,
size - current_size);
}
} while (err == EINTR
&& srv_shutdown_state <= SRV_SHUTDOWN_INITIATED);
......@@ -5459,6 +5468,27 @@ os_file_set_size(
# endif /* HAVE_POSIX_ALLOCATE */
#endif /* _WIN32*/
#ifdef _WIN32
os_offset_t current_size = os_file_get_size(file);
FILE_STORAGE_INFO info;
if (GetFileInformationByHandleEx(file, FileStorageInfo, &info,
sizeof info)) {
if (info.LogicalBytesPerSector) {
current_size &= ~os_offset_t(info.LogicalBytesPerSector
- 1);
}
}
#else
if (fstat(file, &statbuf)) {
return false;
}
os_offset_t current_size = statbuf.st_size
& ~os_offset_t(statbuf.st_blksize - 1);
#endif
if (current_size >= size) {
return true;
}
/* Write up to 1 megabyte at a time. */
ulint buf_size = ut_min(
static_cast<ulint>(64),
......@@ -5476,8 +5506,6 @@ os_file_set_size(
/* Write buffer full of zeros */
memset(buf, 0, buf_size);
os_offset_t current_size = os_file_get_size(file);
while (current_size < size
&& srv_shutdown_state <= SRV_SHUTDOWN_INITIATED) {
ulint n_bytes;
......
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