summaryrefslogtreecommitdiff
path: root/storage/maria/ma_check.c
diff options
context:
space:
mode:
authorMonty <monty@mariadb.org>2020-10-30 15:33:18 +0200
committerMonty <monty@mariadb.org>2020-11-02 17:15:36 +0200
commita876121d24a19340db508f74b1582955c2a168b0 (patch)
tree198ddb428fa0e409caf227fdea63eeef5745de48 /storage/maria/ma_check.c
parente6290a8270daf884f551230307225b358939bfab (diff)
downloadmariadb-git-a876121d24a19340db508f74b1582955c2a168b0.tar.gz
MDEV-23824 SIGSEGV in end_io_cache on REPAIR LOCAL TABLE for Aria table
Bugs fixed: - prepare_for_repair() didn't close all open files if table opened failed because of out-of-memory - If dd_recreate_table() failed, the data file was not properly restored from it's temporary name - Aria repair initializing code didn't properly clear all used structs before calling error, which caused crashed in memory-free calls. - maria_delete_table() didn't register if table open failed. This could calls my_error() to be called without returning 1 to the caller, which cased failures in my_ok() Note when merging to 10.5: - Remove the #if MYSQL_VERSION from sql_admin.cc
Diffstat (limited to 'storage/maria/ma_check.c')
-rw-r--r--storage/maria/ma_check.c34
1 files changed, 24 insertions, 10 deletions
diff --git a/storage/maria/ma_check.c b/storage/maria/ma_check.c
index 20f8eca2828..0f4d79032f8 100644
--- a/storage/maria/ma_check.c
+++ b/storage/maria/ma_check.c
@@ -2344,6 +2344,14 @@ static int initialize_variables_for_repair(HA_CHECK *param,
{
MARIA_SHARE *share= info->s;
+ /*
+ We have to clear these variables first, as the cleanup-in-case-of-error
+ handling may touch these.
+ */
+ bzero((char*) sort_info, sizeof(*sort_info));
+ bzero((char*) sort_param, sizeof(*sort_param));
+ bzero(&info->rec_cache, sizeof(info->rec_cache));
+
if (share->data_file_type == NO_RECORD)
{
_ma_check_print_error(param,
@@ -2358,9 +2366,6 @@ static int initialize_variables_for_repair(HA_CHECK *param,
if (share->lock.update_status)
(*share->lock.update_status)(info);
- bzero((char*) sort_info, sizeof(*sort_info));
- bzero((char*) sort_param, sizeof(*sort_param));
-
param->testflag|= T_REP; /* for easy checking */
if (share->options & (HA_OPTION_CHECKSUM | HA_OPTION_COMPRESS_RECORD))
param->testflag|= T_CALC_CHECKSUM;
@@ -2388,7 +2393,6 @@ static int initialize_variables_for_repair(HA_CHECK *param,
set_data_file_type(sort_info, info->s);
sort_info->org_data_file_type= share->data_file_type;
- bzero(&info->rec_cache, sizeof(info->rec_cache));
info->rec_cache.file= info->dfile.file;
info->update= (short) (HA_STATE_CHANGED | HA_STATE_ROW_CHANGED);
@@ -2869,9 +2873,13 @@ err:
_ma_reset_state(info);
end_io_cache(&param->read_cache);
- end_io_cache(&sort_info.new_info->rec_cache);
+ if (sort_info.new_info)
+ {
+ end_io_cache(&sort_info.new_info->rec_cache);
+ sort_info.new_info->opt_flag&= ~(READ_CACHE_USED | WRITE_CACHE_USED);
+ }
info->opt_flag&= ~(READ_CACHE_USED | WRITE_CACHE_USED);
- sort_info.new_info->opt_flag&= ~(READ_CACHE_USED | WRITE_CACHE_USED);
+
sort_param.sort_info->info->in_check_table= 0;
/* this below could fail, shouldn't we detect error? */
if (got_error)
@@ -4086,10 +4094,13 @@ err:
maria_scan_end(sort_info.info);
_ma_reset_state(info);
- end_io_cache(&sort_info.new_info->rec_cache);
+ if (sort_info.new_info)
+ {
+ end_io_cache(&sort_info.new_info->rec_cache);
+ sort_info.new_info->opt_flag&= ~(READ_CACHE_USED | WRITE_CACHE_USED);
+ }
end_io_cache(&param->read_cache);
info->opt_flag&= ~(READ_CACHE_USED | WRITE_CACHE_USED);
- sort_info.new_info->opt_flag&= ~(READ_CACHE_USED | WRITE_CACHE_USED);
if (got_error)
{
if (! param->error_printed)
@@ -4618,10 +4629,13 @@ err:
the share by remove_io_thread() or it was not yet started (if the
error happend before creating the thread).
*/
- end_io_cache(&sort_info.new_info->rec_cache);
+ if (sort_info.new_info)
+ {
+ end_io_cache(&sort_info.new_info->rec_cache);
+ sort_info.new_info->opt_flag&= ~(READ_CACHE_USED | WRITE_CACHE_USED);
+ }
end_io_cache(&param->read_cache);
info->opt_flag&= ~(READ_CACHE_USED | WRITE_CACHE_USED);
- sort_info.new_info->opt_flag&= ~(READ_CACHE_USED | WRITE_CACHE_USED);
/*
Destroy the new data cache in case of non-quick repair. All slave
threads did either detach from the share by remove_io_thread()