summaryrefslogtreecommitdiff
path: root/sql/sql_base.cc
diff options
context:
space:
mode:
authorunknown <gluh@mysql.com/eagle.(none)>2007-01-10 12:57:03 +0400
committerunknown <gluh@mysql.com/eagle.(none)>2007-01-10 12:57:03 +0400
commitac71a8fa5ee66e72aa55fdccecf1de97cdaefa7c (patch)
treeb730f82adc44728fb33eaf82c96e7d6b0f7798c2 /sql/sql_base.cc
parent8e0eea0d336fe259a753ebc380bc85cf31b29599 (diff)
downloadmariadb-git-ac71a8fa5ee66e72aa55fdccecf1de97cdaefa7c.tar.gz
Fix for bug#20867 InnoDB Bug - create temporary table+crash => mysqld needs to clean up
2nd version During tmp tables cleanup we get the handler for temporary table and delete table using handler method. sql/mysql_priv.h: added function prototype sql/mysqld.cc: added call of mysql_rm_tmp_tables() function sql/sql_base.cc: mysql_rm_tmp_tables() -removed from table_cache_init -During tmp tables cleanup we get the handler for temporary table and delete table using handler method. it allows to remove orphan records from data dictionary(InnoDB)
Diffstat (limited to 'sql/sql_base.cc')
-rw-r--r--sql/sql_base.cc42
1 files changed, 35 insertions, 7 deletions
diff --git a/sql/sql_base.cc b/sql/sql_base.cc
index c60bed09cf9..05ecfe9b484 100644
--- a/sql/sql_base.cc
+++ b/sql/sql_base.cc
@@ -34,7 +34,6 @@ HASH assign_cache;
static int open_unireg_entry(THD *thd,TABLE *entry,const char *db,
const char *name, const char *alias);
static void free_cache_entry(TABLE *entry);
-static void mysql_rm_tmp_tables(void);
extern "C" byte *table_cache_key(const byte *record,uint *length,
@@ -47,7 +46,6 @@ extern "C" byte *table_cache_key(const byte *record,uint *length,
bool table_cache_init(void)
{
- mysql_rm_tmp_tables();
return hash_init(&open_cache, &my_charset_bin, table_cache_size+16,
0, 0,table_cache_key,
(hash_free_key) free_cache_entry, 0) != 0;
@@ -2940,14 +2938,20 @@ fill_record(Field **ptr,List<Item> &values, bool ignore_errors)
}
-static void mysql_rm_tmp_tables(void)
+my_bool mysql_rm_tmp_tables(void)
{
uint i, idx;
- char filePath[FN_REFLEN], *tmpdir;
+ char filePath[FN_REFLEN], *tmpdir, filePathCopy[FN_REFLEN];
MY_DIR *dirp;
FILEINFO *file;
+ TABLE tmp_table;
+ THD *thd;
DBUG_ENTER("mysql_rm_tmp_tables");
+ if (!(thd= new THD))
+ DBUG_RETURN(1);
+ thd->store_globals();
+
for (i=0; i<=mysql_tmpdir_list.max; i++)
{
tmpdir=mysql_tmpdir_list.list[i];
@@ -2968,13 +2972,37 @@ static void mysql_rm_tmp_tables(void)
if (!bcmp(file->name,tmp_file_prefix,tmp_file_prefix_length))
{
- sprintf(filePath,"%s%s",tmpdir,file->name);
- VOID(my_delete(filePath,MYF(MY_WME)));
+ char *ext= fn_ext(file->name);
+ uint ext_len= strlen(ext);
+ uint filePath_len= my_snprintf(filePath, sizeof(filePath),
+ "%s%s", tmpdir, file->name);
+ if (!bcmp(reg_ext, ext, ext_len))
+ {
+ TABLE tmp_table;
+ if (!openfrm(filePath, "tmp_table", (uint) 0,
+ READ_KEYINFO | COMPUTE_TYPES | EXTRA_RECORD,
+ 0, &tmp_table))
+ {
+ /* We should cut file extention before deleting of table */
+ memcpy(filePathCopy, filePath, filePath_len - ext_len);
+ filePathCopy[filePath_len - ext_len]= 0;
+ tmp_table.file->delete_table(filePathCopy);
+ closefrm(&tmp_table);
+ }
+ }
+ /*
+ File can be already deleted by tmp_table.file->delete_table().
+ So we hide error messages which happnes during deleting of these
+ files(MYF(0)).
+ */
+ VOID(my_delete(filePath, MYF(0)));
}
}
my_dirend(dirp);
}
- DBUG_VOID_RETURN;
+ delete thd;
+ my_pthread_setspecific_ptr(THR_THD, 0);
+ DBUG_RETURN(0);
}