Commit 1f040ae0 authored by Monty's avatar Monty

MDEV-34043 Drastically slower query performance between CentOS (2sec) and Rocky (48sec)

One cause of the slowdown is because the ftruncate call can be much
slower on some systems.  ftruncate() is called by Aria for internal
temporary tables, tables created by the optimizer, when the upper level
asks Aria to delete the previous result set. This is needed when some
content from previous tables changes.

I have now changed Aria so that for internal temporary tables we don't
call ftruncate() anymore for maria_delete_all_rows().

I also had to update the Aria repair code to use the logical datafile
size and not the on-disk datafile size, which may contain data from a
previous result set.  The repair code is called to create indexes for
the internal temporary table after it is filled.
I also replaced a call to mysql_file_size() with a pwrite() in
_ma_bitmap_create_first().

Reviewer: Sergei Petrunia <sergey@mariadb.com>
Tester: Dave Gosselin <dave.gosselin@mariadb.com>
parent eadf0f63
......@@ -3070,21 +3070,25 @@ my_bool _ma_check_if_right_bitmap_type(MARIA_HA *info,
int _ma_bitmap_create_first(MARIA_SHARE *share)
{
uint block_size= share->bitmap.block_size;
size_t error;
File file= share->bitmap.file.file;
uchar marker[CRC_SIZE];
uchar *temp_buff;
if (!(temp_buff= (uchar*) my_alloca(block_size)))
return 1;
bzero(temp_buff, block_size);
/*
Next write operation of the page will write correct CRC
if it is needed
*/
int4store(marker, MARIA_NO_CRC_BITMAP_PAGE);
int4store(temp_buff + block_size - CRC_SIZE, MARIA_NO_CRC_BITMAP_PAGE);
if (mysql_file_chsize(file, block_size - sizeof(marker),
0, MYF(MY_WME)) ||
my_pwrite(file, marker, sizeof(marker),
block_size - sizeof(marker),
MYF(MY_NABP | MY_WME)))
error= my_pwrite(file, temp_buff, block_size, 0, MYF(MY_NABP | MY_WME));
my_afree(temp_buff);
if (error)
return 1;
share->state.state.data_file_length= block_size;
_ma_bitmap_delete_all(share);
return 0;
......
......@@ -418,6 +418,8 @@ int maria_chk_size(HA_CHECK *param, register MARIA_HA *info)
/* We cannot check file sizes for S3 */
DBUG_RETURN(0);
}
/* We should never come here with internal temporary tables */
DBUG_ASSERT(!share->internal_table);
if (!(param->testflag & T_SILENT))
puts("- check file-size");
......@@ -713,6 +715,8 @@ static int chk_index_down(HA_CHECK *param, MARIA_HA *info,
MARIA_PAGE ma_page;
DBUG_ENTER("chk_index_down");
DBUG_ASSERT(!share->internal_table);
/* Key blocks must lay within the key file length entirely. */
if (page + keyinfo->block_length > share->state.state.key_file_length)
{
......@@ -2464,7 +2468,16 @@ static int initialize_variables_for_repair(HA_CHECK *param,
return 1;
/* calculate max_records */
if (!share->internal_table)
{
/* Get real file size */
sort_info->filelength= my_seek(info->dfile.file, 0L, MY_SEEK_END, MYF(0));
}
else
{
/* For internal temporary files we are using the logical file length */
sort_info->filelength= share->state.state.data_file_length;
}
param->max_progress= sort_info->filelength;
if ((param->testflag & T_CREATE_MISSING_KEYS) ||
......@@ -2860,7 +2873,8 @@ int maria_repair(HA_CHECK *param, register MARIA_HA *info,
{
fputs(" \r",stdout); fflush(stdout);
}
if (mysql_file_chsize(share->kfile.file,
if (!share->internal_table &&
mysql_file_chsize(share->kfile.file,
share->state.state.key_file_length, 0, MYF(0)))
{
_ma_check_print_warning(param,
......@@ -4168,7 +4182,8 @@ int maria_repair_by_sort(HA_CHECK *param, register MARIA_HA *info,
if (param->testflag & T_CALC_CHECKSUM)
share->state.state.checksum=param->glob_crc;
if (mysql_file_chsize(share->kfile.file,
if (!share->internal_table &&
mysql_file_chsize(share->kfile.file,
share->state.state.key_file_length, 0, MYF(0)))
_ma_check_print_warning(param,
"Can't change size of indexfile, error: %d",
......@@ -4706,7 +4721,8 @@ int maria_repair_parallel(HA_CHECK *param, register MARIA_HA *info,
if (param->testflag & T_CALC_CHECKSUM)
share->state.state.checksum=param->glob_crc;
if (mysql_file_chsize(share->kfile.file,
if (!share->internal_table &&
mysql_file_chsize(share->kfile.file,
share->state.state.key_file_length, 0, MYF(0)))
_ma_check_print_warning(param,
"Can't change size of indexfile, error: %d",
......@@ -6108,6 +6124,8 @@ int maria_test_if_almost_full(MARIA_HA *info)
{
MARIA_SHARE *share= info->s;
DBUG_ASSERT(!share->internal_table);
if (share->options & HA_OPTION_COMPRESS_RECORD)
return 0;
return mysql_file_seek(share->kfile.file, 0L, MY_SEEK_END,
......
......@@ -103,9 +103,17 @@ int maria_delete_all_rows(MARIA_HA *info)
#endif
if (_ma_flush_table_files(info, MARIA_FLUSH_DATA|MARIA_FLUSH_INDEX,
FLUSH_IGNORE_CHANGED, FLUSH_IGNORE_CHANGED) ||
mysql_file_chsize(info->dfile.file, 0, 0, MYF(MY_WME)) ||
mysql_file_chsize(share->kfile.file, share->base.keystart, 0, MYF(MY_WME)))
FLUSH_IGNORE_CHANGED, FLUSH_IGNORE_CHANGED))
goto err;
/*
Avoid truncate of internal temporary tables as this can have a big
performance overhead when called by mysql_handle_single_derived()
tables in MariaDB as part of split materialization.
*/
if (!share->internal_table &&
(mysql_file_chsize(info->dfile.file, 0, 0, MYF(MY_WME)) ||
mysql_file_chsize(share->kfile.file, share->base.keystart, 0,
MYF(MY_WME))))
goto err;
if (_ma_initialize_data_file(share, info->dfile.file))
......
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