BUG#25908 - corrupted myisam table crashes server even after repair
Opening certain tables that have different definitions in .MYI and .frm may result in a server crash. Compare .MYI and .frm definition when myisam table is opened. In case definitions are diffirent refuse to open such table. No test case, since it requires broken table.
This commit is contained in:
parent
94f0977b86
commit
b88e7e0f97
@ -632,6 +632,9 @@ bool ha_myisam::check_if_locking_is_allowed(uint sql_command,
|
||||
|
||||
int ha_myisam::open(const char *name, int mode, uint test_if_locked)
|
||||
{
|
||||
MI_KEYDEF *keyinfo;
|
||||
MI_COLUMNDEF *recinfo= 0;
|
||||
uint recs;
|
||||
uint i;
|
||||
|
||||
/*
|
||||
@ -654,6 +657,26 @@ int ha_myisam::open(const char *name, int mode, uint test_if_locked)
|
||||
|
||||
if (!(file=mi_open(name, mode, test_if_locked | HA_OPEN_FROM_SQL_LAYER)))
|
||||
return (my_errno ? my_errno : -1);
|
||||
if (!table->s->tmp_table) /* No need to perform a check for tmp table */
|
||||
{
|
||||
if ((my_errno= table2myisam(table, &keyinfo, &recinfo, &recs)))
|
||||
{
|
||||
/* purecov: begin inspected */
|
||||
DBUG_PRINT("error", ("Failed to convert TABLE object to MyISAM "
|
||||
"key and column definition"));
|
||||
goto err;
|
||||
/* purecov: end */
|
||||
}
|
||||
if (check_definition(keyinfo, recinfo, table->s->keys, recs,
|
||||
file->s->keyinfo, file->s->rec,
|
||||
file->s->base.keys, file->s->base.fields, true))
|
||||
{
|
||||
/* purecov: begin inspected */
|
||||
my_errno= HA_ERR_CRASHED;
|
||||
goto err;
|
||||
/* purecov: end */
|
||||
}
|
||||
}
|
||||
|
||||
if (test_if_locked & (HA_OPEN_IGNORE_IF_LOCKED | HA_OPEN_TMP_TABLE))
|
||||
VOID(mi_extra(file, HA_EXTRA_NO_WAIT_LOCK, 0));
|
||||
@ -675,6 +698,15 @@ int ha_myisam::open(const char *name, int mode, uint test_if_locked)
|
||||
table->key_info[i].block_size= file->s->keyinfo[i].block_length;
|
||||
}
|
||||
return (0);
|
||||
err:
|
||||
this->close();
|
||||
/*
|
||||
Both recinfo and keydef are allocated by my_multi_malloc(), thus only
|
||||
recinfo must be freed.
|
||||
*/
|
||||
if (recinfo)
|
||||
my_free((gptr) recinfo, MYF(0));
|
||||
return my_errno;
|
||||
}
|
||||
|
||||
int ha_myisam::close(void)
|
||||
|
Loading…
x
Reference in New Issue
Block a user