Commit 3da84d43 authored by tomas@poseidon.ndb.mysql.com's avatar tomas@poseidon.ndb.mysql.com

Merge tulin@bk-internal.mysql.com:/home/bk/mysql-5.0

into poseidon.ndb.mysql.com:/home/tomas/mysql-5.0
parents d6188f9f e70b1c18
...@@ -1150,3 +1150,15 @@ drop table t1; ...@@ -1150,3 +1150,15 @@ drop table t1;
set storage_engine=MyISAM; set storage_engine=MyISAM;
create table t1 (v varchar(65535)); create table t1 (v varchar(65535));
ERROR 42000: Row size too large. The maximum row size for the used table type, not counting BLOBs, is 65535. You have to change some columns to TEXT or BLOBs ERROR 42000: Row size too large. The maximum row size for the used table type, not counting BLOBs, is 65535. You have to change some columns to TEXT or BLOBs
create table t1 (a int) engine=myisam;
drop table if exists t1;
Warnings:
Error 2 Can't find file: 't1' (errno: 2)
create table t1 (a int) engine=myisam;
drop table t1;
ERROR 42S02: Unknown table 't1'
create table t1 (a int) engine=myisam;
drop table t1;
ERROR HY000: File './test/t1.MYD' not found (Errcode: 2)
drop table t1;
ERROR 42S02: Unknown table 't1'
...@@ -180,7 +180,7 @@ select * from t4; ...@@ -180,7 +180,7 @@ select * from t4;
ERROR 42S02: Table 'test.t4' doesn't exist ERROR 42S02: Table 'test.t4' doesn't exist
drop table if exists t4; drop table if exists t4;
Warnings: Warnings:
Note 1051 Unknown table 't4' Error 155 Table 'test.t4' doesn't exist
drop table t5; drop table t5;
ERROR 42S02: Unknown table 't5' ERROR 42S02: Unknown table 't5'
drop table if exists t5; drop table if exists t5;
......
...@@ -6,7 +6,9 @@ drop table if exists t1,t2,t3,t4,t5,t6,t7,t8,t9; ...@@ -6,7 +6,9 @@ drop table if exists t1,t2,t3,t4,t5,t6,t7,t8,t9;
start slave; start slave;
create table t1 (a int) engine=myisam; create table t1 (a int) engine=myisam;
flush tables; flush tables;
drop table t1; drop table if exists t1;
Warnings:
Error 2 Can't find file: 't1' (errno: 2)
create table t1 (a int, unique(a)) engine=myisam; create table t1 (a int, unique(a)) engine=myisam;
set sql_log_bin=0; set sql_log_bin=0;
insert into t1 values(2); insert into t1 values(2);
......
...@@ -539,3 +539,20 @@ eval set storage_engine=$default; ...@@ -539,3 +539,20 @@ eval set storage_engine=$default;
# MyISAM specific varchar tests # MyISAM specific varchar tests
--error 1118 --error 1118
create table t1 (v varchar(65535)); create table t1 (v varchar(65535));
#
# Test how DROP TABLE works if the index or data file doesn't exists
create table t1 (a int) engine=myisam;
system rm ./var/master-data/test/t1.MYI ;
drop table if exists t1;
create table t1 (a int) engine=myisam;
system rm ./var/master-data/test/t1.MYI ;
--error 1051
drop table t1;
create table t1 (a int) engine=myisam;
system rm ./var/master-data/test/t1.MYD ;
--error 1105
drop table t1;
--error 1051
drop table t1;
...@@ -9,7 +9,7 @@ source include/master-slave.inc; ...@@ -9,7 +9,7 @@ source include/master-slave.inc;
create table t1 (a int) engine=myisam; create table t1 (a int) engine=myisam;
flush tables; flush tables;
system rm ./var/master-data/test/t1.MYI ; system rm ./var/master-data/test/t1.MYI ;
drop table t1; drop table if exists t1;
save_master_pos; save_master_pos;
connection slave; connection slave;
sync_with_master; sync_with_master;
......
...@@ -336,6 +336,11 @@ innobase_release_temporary_latches( ...@@ -336,6 +336,11 @@ innobase_release_temporary_latches(
/*===============================*/ /*===============================*/
THD *thd) THD *thd)
{ {
if (!innodb_inited) {
return;
}
trx_t *trx= (trx_t*) thd->ha_data[innobase_hton.slot]; trx_t *trx= (trx_t*) thd->ha_data[innobase_hton.slot];
if (trx) if (trx)
innobase_release_stat_resources(trx); innobase_release_stat_resources(trx);
......
...@@ -1027,15 +1027,24 @@ bool ha_flush_logs() ...@@ -1027,15 +1027,24 @@ bool ha_flush_logs()
The .frm file will be deleted only if we return 0 or ENOENT The .frm file will be deleted only if we return 0 or ENOENT
*/ */
int ha_delete_table(enum db_type table_type, const char *path) int ha_delete_table(THD *thd, enum db_type table_type, const char *path,
const char *alias, bool generate_warning)
{ {
handler *file; handler *file;
char tmp_path[FN_REFLEN]; char tmp_path[FN_REFLEN];
int error;
TABLE dummy_table;
TABLE_SHARE dummy_share;
DBUG_ENTER("ha_delete_table");
bzero((char*) &dummy_table, sizeof(dummy_table));
bzero((char*) &dummy_share, sizeof(dummy_share));
dummy_table.s= &dummy_share;
/* DB_TYPE_UNKNOWN is used in ALTER TABLE when renaming only .frm files */ /* DB_TYPE_UNKNOWN is used in ALTER TABLE when renaming only .frm files */
if (table_type == DB_TYPE_UNKNOWN || if (table_type == DB_TYPE_UNKNOWN ||
! (file=get_new_handler((TABLE*) 0, table_type))) ! (file=get_new_handler(&dummy_table, table_type)))
return ENOENT; DBUG_RETURN(ENOENT);
if (lower_case_table_names == 2 && !(file->table_flags() & HA_FILE_BASED)) if (lower_case_table_names == 2 && !(file->table_flags() & HA_FILE_BASED))
{ {
...@@ -1044,9 +1053,45 @@ int ha_delete_table(enum db_type table_type, const char *path) ...@@ -1044,9 +1053,45 @@ int ha_delete_table(enum db_type table_type, const char *path)
my_casedn_str(files_charset_info, tmp_path); my_casedn_str(files_charset_info, tmp_path);
path= tmp_path; path= tmp_path;
} }
int error=file->delete_table(path); if ((error= file->delete_table(path)) && generate_warning)
{
/*
Because file->print_error() use my_error() to generate the error message
we must store the error state in thd, reset it and restore it to
be able to get hold of the error message.
(We should in the future either rewrite handler::print_error() or make
a nice method of this.
*/
bool query_error= thd->query_error;
sp_rcontext *spcont= thd->spcont;
SELECT_LEX *current_select= thd->lex->current_select;
char buff[sizeof(thd->net.last_error)];
char new_error[sizeof(thd->net.last_error)];
int last_errno= thd->net.last_errno;
strmake(buff, thd->net.last_error, sizeof(buff)-1);
thd->query_error= 0;
thd->spcont= 0;
thd->lex->current_select= 0;
thd->net.last_error[0]= 0;
/* Fill up strucutures that print_error may need */
dummy_table.s->path= path;
dummy_table.alias= alias;
file->print_error(error, 0);
strmake(new_error, thd->net.last_error, sizeof(buff)-1);
/* restore thd */
thd->query_error= query_error;
thd->spcont= spcont;
thd->lex->current_select= current_select;
thd->net.last_errno= last_errno;
strmake(thd->net.last_error, buff, sizeof(buff)-1);
push_warning(thd, MYSQL_ERROR::WARN_LEVEL_ERROR, error, new_error);
}
delete file; delete file;
return error; DBUG_RETURN(error);
} }
/**************************************************************************** /****************************************************************************
...@@ -1320,7 +1365,16 @@ ulonglong handler::get_auto_increment() ...@@ -1320,7 +1365,16 @@ ulonglong handler::get_auto_increment()
return nr; return nr;
} }
/* Print error that we got from handler function */
/*
Print error that we got from handler function
NOTE:
In case of delete table it's only safe to use the following parts of
the 'table' structure:
table->s->path
table->alias
*/
void handler::print_error(int error, myf errflag) void handler::print_error(int error, myf errflag)
{ {
...@@ -1499,16 +1553,38 @@ uint handler::get_dup_key(int error) ...@@ -1499,16 +1553,38 @@ uint handler::get_dup_key(int error)
} }
/*
Delete all files with extension from bas_ext()
SYNOPSIS
delete_table()
name Base name of table
NOTES
We assume that the handler may return more extensions than
was actually used for the file.
RETURN
0 If we successfully deleted at least one file from base_ext and
didn't get any other errors than ENOENT
# Error from delete_file()
*/
int handler::delete_table(const char *name) int handler::delete_table(const char *name)
{ {
int error=0; int error= 0;
int enoent_or_zero= ENOENT; // Error if no file was deleted
for (const char **ext=bas_ext(); *ext ; ext++) for (const char **ext=bas_ext(); *ext ; ext++)
{ {
if (delete_file(name,*ext,2)) if (delete_file(name,*ext,2))
{ {
if ((error=errno) != ENOENT) if ((error= my_errno) != ENOENT)
break; break;
} }
else
enoent_or_zero= 0; // No error for ENOENT
error= enoent_or_zero;
} }
return error; return error;
} }
......
...@@ -217,11 +217,13 @@ struct xid_t { ...@@ -217,11 +217,13 @@ struct xid_t {
bool eq(long g, long b, const char *d) bool eq(long g, long b, const char *d)
{ return g == gtrid_length && b == bqual_length && !memcmp(d, data, g+b); } { return g == gtrid_length && b == bqual_length && !memcmp(d, data, g+b); }
void set(LEX_STRING *l) { set(l->length, 0, l->str); } void set(LEX_STRING *l) { set(l->length, 0, l->str); }
void set(ulonglong l) void set(ulonglong xid)
{ {
my_xid tmp;
set(MYSQL_XID_PREFIX_LEN, 0, MYSQL_XID_PREFIX); set(MYSQL_XID_PREFIX_LEN, 0, MYSQL_XID_PREFIX);
*(ulong*)(data+MYSQL_XID_PREFIX_LEN)=server_id; memcpy(data+MYSQL_XID_PREFIX_LEN, &server_id, sizeof(server_id));
*(my_xid*)(data+MYSQL_XID_OFFSET)=l; tmp= xid;
memcpy(data+MYSQL_XID_OFFSET, &tmp, sizeof(tmp));
gtrid_length=MYSQL_XID_GTRID_LEN; gtrid_length=MYSQL_XID_GTRID_LEN;
} }
void set(long g, long b, const char *d) void set(long g, long b, const char *d)
...@@ -235,7 +237,9 @@ struct xid_t { ...@@ -235,7 +237,9 @@ struct xid_t {
void null() { formatID= -1; } void null() { formatID= -1; }
my_xid quick_get_my_xid() my_xid quick_get_my_xid()
{ {
return *(my_xid*)(data+MYSQL_XID_OFFSET); my_xid tmp;
memcpy(&tmp, data+MYSQL_XID_OFFSET, sizeof(tmp));
return tmp;
} }
my_xid get_my_xid() my_xid get_my_xid()
{ {
...@@ -753,7 +757,8 @@ bool ha_flush_logs(void); ...@@ -753,7 +757,8 @@ bool ha_flush_logs(void);
void ha_drop_database(char* path); void ha_drop_database(char* path);
int ha_create_table(const char *name, HA_CREATE_INFO *create_info, int ha_create_table(const char *name, HA_CREATE_INFO *create_info,
bool update_create_info); bool update_create_info);
int ha_delete_table(enum db_type db_type, const char *path); int ha_delete_table(THD *thd, enum db_type db_type, const char *path,
const char *alias, bool generate_warning);
/* discovery */ /* discovery */
int ha_create_table_from_engine(THD* thd, const char *db, const char *name, int ha_create_table_from_engine(THD* thd, const char *db, const char *name,
......
...@@ -920,6 +920,13 @@ bool MYSQL_LOG::reset_logs(THD* thd) ...@@ -920,6 +920,13 @@ bool MYSQL_LOG::reset_logs(THD* thd)
*/ */
pthread_mutex_lock(&LOCK_log); pthread_mutex_lock(&LOCK_log);
pthread_mutex_lock(&LOCK_index); pthread_mutex_lock(&LOCK_index);
/*
The following mutex is needed to ensure that no threads call
'delete thd' as we would then risk missing a 'rollback' from this
thread. If the transaction involved MyISAM tables, it should go
into binlog even on rollback.
*/
(void) pthread_mutex_lock(&LOCK_thread_count);
/* Save variables so that we can reopen the log */ /* Save variables so that we can reopen the log */
save_name=name; save_name=name;
...@@ -953,6 +960,7 @@ bool MYSQL_LOG::reset_logs(THD* thd) ...@@ -953,6 +960,7 @@ bool MYSQL_LOG::reset_logs(THD* thd)
my_free((gptr) save_name, MYF(0)); my_free((gptr) save_name, MYF(0));
err: err:
(void) pthread_mutex_unlock(&LOCK_thread_count);
pthread_mutex_unlock(&LOCK_index); pthread_mutex_unlock(&LOCK_index);
pthread_mutex_unlock(&LOCK_log); pthread_mutex_unlock(&LOCK_log);
DBUG_RETURN(error); DBUG_RETURN(error);
...@@ -1601,7 +1609,8 @@ bool MYSQL_LOG::write(Log_event* event_info) ...@@ -1601,7 +1609,8 @@ bool MYSQL_LOG::write(Log_event* event_info)
{ {
thd->ha_data[binlog_hton.slot]= trans_log= (IO_CACHE *) thd->ha_data[binlog_hton.slot]= trans_log= (IO_CACHE *)
my_malloc(sizeof(IO_CACHE), MYF(MY_ZEROFILL)); my_malloc(sizeof(IO_CACHE), MYF(MY_ZEROFILL));
if (!trans_log || open_cached_file(trans_log, mysql_tmpdir, LOG_PREFIX, if (!trans_log || open_cached_file(trans_log, mysql_tmpdir,
LOG_PREFIX,
binlog_cache_size, MYF(MY_WME))) binlog_cache_size, MYF(MY_WME)))
{ {
my_free((gptr)trans_log, MYF(MY_ALLOW_ZERO_PTR)); my_free((gptr)trans_log, MYF(MY_ALLOW_ZERO_PTR));
...@@ -1610,12 +1619,14 @@ bool MYSQL_LOG::write(Log_event* event_info) ...@@ -1610,12 +1619,14 @@ bool MYSQL_LOG::write(Log_event* event_info)
} }
trans_log->end_of_file= max_binlog_cache_size; trans_log->end_of_file= max_binlog_cache_size;
trans_register_ha(thd, trans_register_ha(thd,
thd->options & (OPTION_NOT_AUTOCOMMIT | OPTION_BEGIN), thd->options & (OPTION_NOT_AUTOCOMMIT |
OPTION_BEGIN),
&binlog_hton); &binlog_hton);
} }
else if (!my_b_tell(trans_log)) else if (!my_b_tell(trans_log))
trans_register_ha(thd, trans_register_ha(thd,
thd->options & (OPTION_NOT_AUTOCOMMIT | OPTION_BEGIN), thd->options & (OPTION_NOT_AUTOCOMMIT |
OPTION_BEGIN),
&binlog_hton); &binlog_hton);
file= trans_log; file= trans_log;
} }
...@@ -1804,9 +1815,9 @@ uint MYSQL_LOG::next_file_id() ...@@ -1804,9 +1815,9 @@ uint MYSQL_LOG::next_file_id()
IMPLEMENTATION IMPLEMENTATION
- To support transaction over replication, we wrap the transaction - To support transaction over replication, we wrap the transaction
with BEGIN/COMMIT or BEGIN/ROLLBACK in the binary log. with BEGIN/COMMIT or BEGIN/ROLLBACK in the binary log.
We want to write a BEGIN/ROLLBACK block when a non-transactional table was We want to write a BEGIN/ROLLBACK block when a non-transactional table
updated in a transaction which was rolled back. This is to ensure that the was updated in a transaction which was rolled back. This is to ensure
same updates are run on the slave. that the same updates are run on the slave.
*/ */
bool MYSQL_LOG::write(THD *thd, IO_CACHE *cache) bool MYSQL_LOG::write(THD *thd, IO_CACHE *cache)
...@@ -2475,15 +2486,13 @@ int TC_LOG_MMAP::open(const char *opt_name) ...@@ -2475,15 +2486,13 @@ int TC_LOG_MMAP::open(const char *opt_name)
DBUG_ASSERT(TC_LOG_PAGE_SIZE % tc_log_page_size == 0); DBUG_ASSERT(TC_LOG_PAGE_SIZE % tc_log_page_size == 0);
fn_format(logname,opt_name,mysql_data_home,"",MY_UNPACK_FILENAME); fn_format(logname,opt_name,mysql_data_home,"",MY_UNPACK_FILENAME);
fd= my_open(logname, O_RDWR, MYF(0)); if ((fd= my_open(logname, O_RDWR, MYF(0))) < 0)
if (fd == -1)
{ {
if (my_errno != ENOENT) if (my_errno != ENOENT)
goto err; goto err;
if (using_heuristic_recover()) if (using_heuristic_recover())
return 1; return 1;
fd= my_create(logname, O_RDWR, 0, MYF(MY_WME)); if ((fd= my_create(logname, O_RDWR, 0, MYF(MY_WME))) < 0)
if (fd == -1)
goto err; goto err;
inited=1; inited=1;
file_length= opt_tc_log_size; file_length= opt_tc_log_size;
...@@ -2821,7 +2830,7 @@ int TC_LOG_MMAP::recover() ...@@ -2821,7 +2830,7 @@ int TC_LOG_MMAP::recover()
*/ */
if (data[sizeof(tc_log_magic)] != total_ha_2pc) if (data[sizeof(tc_log_magic)] != total_ha_2pc)
{ {
sql_print_error("Recovery failed! You must have enabled " sql_print_error("Recovery failed! You must enable "
"exactly %d storage engines that support " "exactly %d storage engines that support "
"two-phase commit protocol", "two-phase commit protocol",
data[sizeof(tc_log_magic)]); data[sizeof(tc_log_magic)]);
...@@ -2930,15 +2939,16 @@ int TC_LOG_BINLOG::open(const char *opt_name) ...@@ -2930,15 +2939,16 @@ int TC_LOG_BINLOG::open(const char *opt_name)
if (! fdle.is_valid()) if (! fdle.is_valid())
goto err; goto err;
for (error= 0; !error ;) do
{ {
strnmov(log_name, log_info.log_file_name, sizeof(log_name)); strmake(log_name, log_info.log_file_name, sizeof(log_name)-1);
if ((error= find_next_log(&log_info, 1)) != LOG_INFO_EOF) } while (!(error= find_next_log(&log_info, 1)));
if (error != LOG_INFO_EOF)
{ {
sql_print_error("find_log_pos() failed (error: %d)", error); sql_print_error("find_log_pos() failed (error: %d)", error);
goto err; goto err;
} }
}
if ((file= open_binlog(&log, log_name, &errmsg)) < 0) if ((file= open_binlog(&log, log_name, &errmsg)) < 0)
{ {
......
...@@ -3099,12 +3099,14 @@ void Xid_log_event::pack_info(Protocol *protocol) ...@@ -3099,12 +3099,14 @@ void Xid_log_event::pack_info(Protocol *protocol)
we don't care about actual values of xids as long as we don't care about actual values of xids as long as
identical numbers compare identically identical numbers compare identically
*/ */
Xid_log_event::Xid_log_event(const char* buf,
const Format_description_log_event* description_event) Xid_log_event::
Xid_log_event(const char* buf,
const Format_description_log_event *description_event)
:Log_event(buf, description_event) :Log_event(buf, description_event)
{ {
buf+= description_event->common_header_len; buf+= description_event->common_header_len;
xid=*((my_xid *)buf); memcpy((char*) &xid, buf, sizeof(xid));
} }
......
...@@ -204,20 +204,16 @@ my_bool acl_init(THD *org_thd, bool dont_read_acl_tables) ...@@ -204,20 +204,16 @@ my_bool acl_init(THD *org_thd, bool dont_read_acl_tables)
if (lower_case_table_names) if (lower_case_table_names)
{ {
/* /*
We make a temporary copy of the database, force it to lower case, convert db to lower case and give a warning if the db wasn't
and then copy it back over the original name. We can't just update already in lower case
the host.db pointer, because tmp_name is allocated on the stack.
*/ */
(void)strmov(tmp_name, host.db); (void) strmov(tmp_name, host.db);
my_casedn_str(files_charset_info, tmp_name); my_casedn_str(files_charset_info, host.db);
if (strcmp(host.db, tmp_name) != 0) if (strcmp(host.db, tmp_name) != 0)
{
sql_print_warning("'host' entry '%s|%s' had database in mixed " sql_print_warning("'host' entry '%s|%s' had database in mixed "
"case that has been forced to lowercase because " "case that has been forced to lowercase because "
"lower_case_table_names is set.", "lower_case_table_names is set.",
host.host.hostname, host.db); host.host.hostname, host.db);
(void)strmov(host.db, tmp_name);
}
} }
host.access= get_access(table,2); host.access= get_access(table,2);
host.access= fix_rights_for_db(host.access); host.access= fix_rights_for_db(host.access);
...@@ -432,19 +428,17 @@ my_bool acl_init(THD *org_thd, bool dont_read_acl_tables) ...@@ -432,19 +428,17 @@ my_bool acl_init(THD *org_thd, bool dont_read_acl_tables)
if (lower_case_table_names) if (lower_case_table_names)
{ {
/* /*
We make a temporary copy of the database, force it to lower case, convert db to lower case and give a warning if the db wasn't
and then copy it back over the original name. We can't just update already in lower case
the db.db pointer, because tmp_name is allocated on the stack.
*/ */
(void)strmov(tmp_name, db.db); (void)strmov(tmp_name, db.db);
my_casedn_str(files_charset_info, tmp_name); my_casedn_str(files_charset_info, db.db);
if (strcmp(db.db, tmp_name) != 0) if (strcmp(db.db, tmp_name) != 0)
{ {
sql_print_warning("'db' entry '%s %s@%s' had database in mixed " sql_print_warning("'db' entry '%s %s@%s' had database in mixed "
"case that has been forced to lowercase because " "case that has been forced to lowercase because "
"lower_case_table_names is set.", "lower_case_table_names is set.",
db.db, db.user, db.host.hostname, db.host.hostname); db.db, db.user, db.host.hostname, db.host.hostname);
(void)strmov(db.db, tmp_name);
} }
} }
db.sort=get_sort(3,db.host.hostname,db.db,db.user); db.sort=get_sort(3,db.host.hostname,db.db,db.user);
......
...@@ -3592,23 +3592,20 @@ static void mysql_rm_tmp_tables(void) ...@@ -3592,23 +3592,20 @@ static void mysql_rm_tmp_tables(void)
*****************************************************************************/ *****************************************************************************/
/* /*
** Invalidate any cache entries that are for some DB Invalidate any cache entries that are for some DB
** We can't use hash_delete when looping hash_elements. We mark them first
** and afterwards delete those marked unused. SYNOPSIS
remove_db_from_cache()
db Database name. This will be in lower case if
lower_case_table_name is set
NOTE:
We can't use hash_delete when looping hash_elements. We mark them first
and afterwards delete those marked unused.
*/ */
void remove_db_from_cache(const char *db) void remove_db_from_cache(const char *db)
{ {
char name_buff[NAME_LEN+1];
if (db && lower_case_table_names)
{
/*
convert database to lower case for comparision.
*/
strmake(name_buff, db, sizeof(name_buff)-1);
my_casedn_str(files_charset_info, name_buff);
db= name_buff;
}
for (uint idx=0 ; idx < open_cache.records ; idx++) for (uint idx=0 ; idx < open_cache.records ; idx++)
{ {
TABLE *table=(TABLE*) hash_element(&open_cache,idx); TABLE *table=(TABLE*) hash_element(&open_cache,idx);
......
...@@ -576,7 +576,8 @@ exit2: ...@@ -576,7 +576,8 @@ exit2:
mysql_rm_db() mysql_rm_db()
thd Thread handle thd Thread handle
db Database name in the case given by user db Database name in the case given by user
It's already validated when we come here It's already validated and set to lower case
(if needed) when we come here
if_exists Don't give error if database doesn't exists if_exists Don't give error if database doesn't exists
silent Don't generate errors silent Don't generate errors
...@@ -589,7 +590,7 @@ bool mysql_rm_db(THD *thd,char *db,bool if_exists, bool silent) ...@@ -589,7 +590,7 @@ bool mysql_rm_db(THD *thd,char *db,bool if_exists, bool silent)
{ {
long deleted=0; long deleted=0;
int error= 0; int error= 0;
char path[FN_REFLEN+16], tmp_db[NAME_LEN+1]; char path[FN_REFLEN+16];
MY_DIR *dirp; MY_DIR *dirp;
uint length; uint length;
DBUG_ENTER("mysql_rm_db"); DBUG_ENTER("mysql_rm_db");
...@@ -636,13 +637,6 @@ bool mysql_rm_db(THD *thd,char *db,bool if_exists, bool silent) ...@@ -636,13 +637,6 @@ bool mysql_rm_db(THD *thd,char *db,bool if_exists, bool silent)
error = 0; error = 0;
} }
} }
if (lower_case_table_names)
{
/* Convert database to lower case */
strmov(tmp_db, db);
my_casedn_str(files_charset_info, tmp_db);
db= tmp_db;
}
if (!silent && deleted>=0) if (!silent && deleted>=0)
{ {
const char *query; const char *query;
......
...@@ -1775,8 +1775,7 @@ bool dispatch_command(enum enum_server_command command, THD *thd, ...@@ -1775,8 +1775,7 @@ bool dispatch_command(enum enum_server_command command, THD *thd,
break; break;
} }
mysql_log.write(thd,command,db); mysql_log.write(thd,command,db);
mysql_rm_db(thd, (lower_case_table_names == 2 ? alias : db), mysql_rm_db(thd, db, 0, 0);
0, 0);
break; break;
} }
#ifndef EMBEDDED_LIBRARY #ifndef EMBEDDED_LIBRARY
...@@ -3223,8 +3222,6 @@ unsent_create_error: ...@@ -3223,8 +3222,6 @@ unsent_create_error:
/* revert changes for SP */ /* revert changes for SP */
lex->select_lex.table_list.first= (byte*) first_table; lex->select_lex.table_list.first= (byte*) first_table;
} }
else
res= TRUE;
if (first_table->view && !first_table->contain_auto_increment) if (first_table->view && !first_table->contain_auto_increment)
thd->last_insert_id= 0; // do not show last insert ID if VIEW have not it thd->last_insert_id= 0; // do not show last insert ID if VIEW have not it
...@@ -3309,7 +3306,7 @@ unsent_create_error: ...@@ -3309,7 +3306,7 @@ unsent_create_error:
delete result; delete result;
} }
else else
res= TRUE; res= TRUE; // Error
break; break;
} }
case SQLCOM_DROP_TABLE: case SQLCOM_DROP_TABLE:
...@@ -3535,8 +3532,7 @@ unsent_create_error: ...@@ -3535,8 +3532,7 @@ unsent_create_error:
ER(ER_LOCK_OR_ACTIVE_TRANSACTION), MYF(0)); ER(ER_LOCK_OR_ACTIVE_TRANSACTION), MYF(0));
goto error; goto error;
} }
res=mysql_rm_db(thd, (lower_case_table_names == 2 ? alias : lex->name), res= mysql_rm_db(thd, lex->name, lex->drop_if_exists, 0);
lex->drop_if_exists, 0);
break; break;
} }
case SQLCOM_ALTER_DB: case SQLCOM_ALTER_DB:
...@@ -3873,10 +3869,7 @@ unsent_create_error: ...@@ -3873,10 +3869,7 @@ unsent_create_error:
*sv=(*sv)->prev; *sv=(*sv)->prev;
} }
else else
{
my_error(ER_SP_DOES_NOT_EXIST, MYF(0), "SAVEPOINT", lex->ident.str); my_error(ER_SP_DOES_NOT_EXIST, MYF(0), "SAVEPOINT", lex->ident.str);
res= TRUE;
}
break; break;
} }
case SQLCOM_ROLLBACK_TO_SAVEPOINT: case SQLCOM_ROLLBACK_TO_SAVEPOINT:
...@@ -3905,10 +3898,7 @@ unsent_create_error: ...@@ -3905,10 +3898,7 @@ unsent_create_error:
*sv=(*sv)->prev; *sv=(*sv)->prev;
} }
else else
{
my_error(ER_SP_DOES_NOT_EXIST, MYF(0), "SAVEPOINT", lex->ident.str); my_error(ER_SP_DOES_NOT_EXIST, MYF(0), "SAVEPOINT", lex->ident.str);
res= TRUE;
}
break; break;
} }
case SQLCOM_SAVEPOINT: case SQLCOM_SAVEPOINT:
...@@ -3935,7 +3925,6 @@ unsent_create_error: ...@@ -3935,7 +3925,6 @@ unsent_create_error:
savepoint_alloc_size)) == 0) savepoint_alloc_size)) == 0)
{ {
my_error(ER_OUT_OF_RESOURCES, MYF(0)); my_error(ER_OUT_OF_RESOURCES, MYF(0));
res= TRUE;
break; break;
} }
newsv->name=strmake_root(&thd->transaction.mem_root, newsv->name=strmake_root(&thd->transaction.mem_root,
...@@ -4341,7 +4330,6 @@ unsent_create_error: ...@@ -4341,7 +4330,6 @@ unsent_create_error:
} }
thd->transaction.xa_state=XA_ACTIVE; thd->transaction.xa_state=XA_ACTIVE;
send_ok(thd); send_ok(thd);
res=TRUE;
break; break;
} }
if (thd->lex->ident.length > MAXGTRIDSIZE || thd->lex->xa_opt != XA_NONE) if (thd->lex->ident.length > MAXGTRIDSIZE || thd->lex->xa_opt != XA_NONE)
...@@ -4367,7 +4355,6 @@ unsent_create_error: ...@@ -4367,7 +4355,6 @@ unsent_create_error:
OPTION_BEGIN); OPTION_BEGIN);
thd->server_status|= SERVER_STATUS_IN_TRANS; thd->server_status|= SERVER_STATUS_IN_TRANS;
send_ok(thd); send_ok(thd);
res=TRUE;
break; break;
case SQLCOM_XA_END: case SQLCOM_XA_END:
/* fake it */ /* fake it */
...@@ -4389,7 +4376,6 @@ unsent_create_error: ...@@ -4389,7 +4376,6 @@ unsent_create_error:
} }
thd->transaction.xa_state=XA_IDLE; thd->transaction.xa_state=XA_IDLE;
send_ok(thd); send_ok(thd);
res=TRUE;
break; break;
case SQLCOM_XA_PREPARE: case SQLCOM_XA_PREPARE:
if (thd->transaction.xa_state != XA_IDLE) if (thd->transaction.xa_state != XA_IDLE)
...@@ -4409,7 +4395,6 @@ unsent_create_error: ...@@ -4409,7 +4395,6 @@ unsent_create_error:
thd->transaction.xa_state=XA_NOTR; thd->transaction.xa_state=XA_NOTR;
break; break;
} }
res=TRUE;
thd->transaction.xa_state=XA_PREPARED; thd->transaction.xa_state=XA_PREPARED;
send_ok(thd); send_ok(thd);
break; break;
...@@ -4428,7 +4413,6 @@ unsent_create_error: ...@@ -4428,7 +4413,6 @@ unsent_create_error:
else else
{ {
send_ok(thd); send_ok(thd);
res= TRUE;
} }
} }
else else
...@@ -4439,7 +4423,6 @@ unsent_create_error: ...@@ -4439,7 +4423,6 @@ unsent_create_error:
else else
{ {
send_ok(thd); send_ok(thd);
res= TRUE;
} }
} }
else else
...@@ -4469,16 +4452,13 @@ unsent_create_error: ...@@ -4469,16 +4452,13 @@ unsent_create_error:
if (ha_rollback(thd)) if (ha_rollback(thd))
my_error(ER_XAER_RMERR, MYF(0)); my_error(ER_XAER_RMERR, MYF(0));
else else
{
send_ok(thd); send_ok(thd);
res= TRUE;
}
thd->options&= ~(ulong) (OPTION_BEGIN | OPTION_STATUS_NO_TRANS_UPDATE); thd->options&= ~(ulong) (OPTION_BEGIN | OPTION_STATUS_NO_TRANS_UPDATE);
thd->server_status&= ~SERVER_STATUS_IN_TRANS; thd->server_status&= ~SERVER_STATUS_IN_TRANS;
thd->transaction.xa_state=XA_NOTR; thd->transaction.xa_state=XA_NOTR;
break; break;
case SQLCOM_XA_RECOVER: case SQLCOM_XA_RECOVER:
res= !mysql_xa_recover(thd); res= mysql_xa_recover(thd);
break; break;
default: default:
DBUG_ASSERT(0); /* Impossible */ DBUG_ASSERT(0); /* Impossible */
......
...@@ -454,13 +454,14 @@ impossible position"; ...@@ -454,13 +454,14 @@ impossible position";
(*packet)[EVENT_TYPE_OFFSET+1])); (*packet)[EVENT_TYPE_OFFSET+1]));
if ((*packet)[EVENT_TYPE_OFFSET+1] == FORMAT_DESCRIPTION_EVENT) if ((*packet)[EVENT_TYPE_OFFSET+1] == FORMAT_DESCRIPTION_EVENT)
{ {
binlog_can_be_corrupted= (*packet)[FLAGS_OFFSET+1] & LOG_EVENT_BINLOG_IN_USE_F; binlog_can_be_corrupted= test((*packet)[FLAGS_OFFSET+1] &
LOG_EVENT_BINLOG_IN_USE_F);
/* /*
mark that this event with "log_pos=0", so the slave mark that this event with "log_pos=0", so the slave
should not increment master's binlog position should not increment master's binlog position
(rli->group_master_log_pos) (rli->group_master_log_pos)
*/ */
int4store(packet->c_ptr()+LOG_POS_OFFSET+1, 0); int4store((char*) packet->ptr()+LOG_POS_OFFSET+1, 0);
/* send it */ /* send it */
if (my_net_write(net, (char*)packet->ptr(), packet->length())) if (my_net_write(net, (char*)packet->ptr(), packet->length()))
{ {
...@@ -477,16 +478,21 @@ impossible position"; ...@@ -477,16 +478,21 @@ impossible position";
} }
} }
else else
{
if (test_for_non_eof_log_read_errors(error, &errmsg)) if (test_for_non_eof_log_read_errors(error, &errmsg))
goto err; goto err;
/* /*
else: it's EOF, nothing to do, go on reading next events, the It's EOF, nothing to do, go on reading next events, the
Format_description_log_event will be found naturally if it is written. Format_description_log_event will be found naturally if it is written.
*/ */
}
/* reset the packet as we wrote to it in any case */ /* reset the packet as we wrote to it in any case */
packet->set("\0", 1, &my_charset_bin); packet->set("\0", 1, &my_charset_bin);
} /* end of if (pos > BIN_LOG_HEADER_SIZE); if false, the } /* end of if (pos > BIN_LOG_HEADER_SIZE); */
Format_description_log_event event will be found naturally. */ else
{
/* The Format_description_log_event event will be found naturally. */
}
/* seek to the requested position, to start the requested dump */ /* seek to the requested position, to start the requested dump */
my_b_seek(&log, pos); // Seek will done on next read my_b_seek(&log, pos); // Seek will done on next read
...@@ -506,7 +512,8 @@ impossible position"; ...@@ -506,7 +512,8 @@ impossible position";
#endif #endif
if ((*packet)[EVENT_TYPE_OFFSET+1] == FORMAT_DESCRIPTION_EVENT) if ((*packet)[EVENT_TYPE_OFFSET+1] == FORMAT_DESCRIPTION_EVENT)
binlog_can_be_corrupted= (*packet)[FLAGS_OFFSET+1] & LOG_EVENT_BINLOG_IN_USE_F; binlog_can_be_corrupted= test((*packet)[FLAGS_OFFSET+1] &
LOG_EVENT_BINLOG_IN_USE_F);
else if ((*packet)[EVENT_TYPE_OFFSET+1] == STOP_EVENT) else if ((*packet)[EVENT_TYPE_OFFSET+1] == STOP_EVENT)
binlog_can_be_corrupted= FALSE; binlog_can_be_corrupted= FALSE;
...@@ -810,7 +817,8 @@ int start_slave(THD* thd , MASTER_INFO* mi, bool net_report) ...@@ -810,7 +817,8 @@ int start_slave(THD* thd , MASTER_INFO* mi, bool net_report)
/* Issuing warning then started without --skip-slave-start */ /* Issuing warning then started without --skip-slave-start */
if (!opt_skip_slave_start) if (!opt_skip_slave_start)
push_warning(thd, MYSQL_ERROR::WARN_LEVEL_NOTE, ER_MISSING_SKIP_SLAVE, push_warning(thd, MYSQL_ERROR::WARN_LEVEL_NOTE,
ER_MISSING_SKIP_SLAVE,
ER(ER_MISSING_SKIP_SLAVE)); ER(ER_MISSING_SKIP_SLAVE));
} }
...@@ -831,9 +839,11 @@ int start_slave(THD* thd , MASTER_INFO* mi, bool net_report) ...@@ -831,9 +839,11 @@ int start_slave(THD* thd , MASTER_INFO* mi, bool net_report)
slave_errno = ER_BAD_SLAVE; slave_errno = ER_BAD_SLAVE;
} }
else else
//no error if all threads are already started, only a warning {
/* no error if all threads are already started, only a warning */
push_warning(thd, MYSQL_ERROR::WARN_LEVEL_NOTE, ER_SLAVE_WAS_RUNNING, push_warning(thd, MYSQL_ERROR::WARN_LEVEL_NOTE, ER_SLAVE_WAS_RUNNING,
ER(ER_SLAVE_WAS_RUNNING)); ER(ER_SLAVE_WAS_RUNNING));
}
unlock_slave_threads(mi); unlock_slave_threads(mi);
......
...@@ -113,7 +113,8 @@ bool mysql_rm_table(THD *thd,TABLE_LIST *tables, my_bool if_exists, ...@@ -113,7 +113,8 @@ bool mysql_rm_table(THD *thd,TABLE_LIST *tables, my_bool if_exists,
thd Thread handle thd Thread handle
tables List of tables to delete tables List of tables to delete
if_exists If 1, don't give error if one table doesn't exists if_exists If 1, don't give error if one table doesn't exists
dont_log_query Don't write query to log files dont_log_query Don't write query to log files. This will also not
generate warnings if the handler files doesn't exists
NOTES NOTES
Works like documented in mysql_rm_table(), but don't check Works like documented in mysql_rm_table(), but don't check
...@@ -157,7 +158,8 @@ int mysql_rm_table_part2_with_lock(THD *thd, ...@@ -157,7 +158,8 @@ int mysql_rm_table_part2_with_lock(THD *thd,
In this case we give an warning of level 'NOTE' In this case we give an warning of level 'NOTE'
drop_temporary Only drop temporary tables drop_temporary Only drop temporary tables
drop_view Allow to delete VIEW .frm drop_view Allow to delete VIEW .frm
dont_log_query Don't log the query dont_log_query Don't write query to log files. This will also not
generate warnings if the handler files doesn't exists
TODO: TODO:
When logging to the binary log, we should log When logging to the binary log, we should log
...@@ -218,7 +220,8 @@ int mysql_rm_table_part2(THD *thd, TABLE_LIST *tables, bool if_exists, ...@@ -218,7 +220,8 @@ int mysql_rm_table_part2(THD *thd, TABLE_LIST *tables, bool if_exists,
(void) unpack_filename(path,path); (void) unpack_filename(path,path);
} }
if (drop_temporary || if (drop_temporary ||
(access(path,F_OK) && ha_create_table_from_engine(thd,db,alias,TRUE)) || (access(path,F_OK) &&
ha_create_table_from_engine(thd,db,alias,TRUE)) ||
(!drop_view && mysql_frm_type(path) != FRMTYPE_TABLE)) (!drop_view && mysql_frm_type(path) != FRMTYPE_TABLE))
{ {
if (if_exists) if (if_exists)
...@@ -233,35 +236,23 @@ int mysql_rm_table_part2(THD *thd, TABLE_LIST *tables, bool if_exists, ...@@ -233,35 +236,23 @@ int mysql_rm_table_part2(THD *thd, TABLE_LIST *tables, bool if_exists,
char *end; char *end;
db_type table_type= get_table_type(path); db_type table_type= get_table_type(path);
*(end=fn_ext(path))=0; // Remove extension for delete *(end=fn_ext(path))=0; // Remove extension for delete
error=ha_delete_table(table_type, path); error= ha_delete_table(thd, table_type, path, table->table_name,
if (error == ENOENT && if_exists) !dont_log_query);
error = 0; if ((error == ENOENT || error == HA_ERR_NO_SUCH_TABLE) && if_exists)
error= 0;
if (error == HA_ERR_ROW_IS_REFERENCED) if (error == HA_ERR_ROW_IS_REFERENCED)
{ {
/* the table is referenced by a foreign key constraint */ /* the table is referenced by a foreign key constraint */
foreign_key_error=1; foreign_key_error=1;
} }
if (!error || error == ENOENT) if (!error || error == ENOENT || error == HA_ERR_NO_SUCH_TABLE)
{ {
int new_error;
/* Delete the table definition file */ /* Delete the table definition file */
strmov(end,reg_ext); strmov(end,reg_ext);
if (!(error=my_delete(path,MYF(MY_WME)))) if (!(new_error=my_delete(path,MYF(MY_WME))))
some_tables_deleted=1;
}
if (error == HA_ERR_NO_SUCH_TABLE)
{
/* The table did not exist in engine */
if (if_exists)
{
push_warning_printf(thd, MYSQL_ERROR::WARN_LEVEL_NOTE,
ER_BAD_TABLE_ERROR, ER(ER_BAD_TABLE_ERROR),
table->table_name);
error= 0;
}
/* Delete the table definition file */
strmov(end,reg_ext);
if (!(my_delete(path,MYF(MY_WME))))
some_tables_deleted=1; some_tables_deleted=1;
error|= new_error;
} }
} }
if (error) if (error)
...@@ -311,7 +302,7 @@ int quick_rm_table(enum db_type base,const char *db, ...@@ -311,7 +302,7 @@ int quick_rm_table(enum db_type base,const char *db,
error=1; /* purecov: inspected */ error=1; /* purecov: inspected */
my_snprintf(path, sizeof(path), "%s/%s/%s", mysql_data_home, db, table_name); my_snprintf(path, sizeof(path), "%s/%s/%s", mysql_data_home, db, table_name);
unpack_filename(path,path); unpack_filename(path,path);
return ha_delete_table(base,path) || error; return ha_delete_table(current_thd, base, path, table_name, 0) || error;
} }
/* /*
......
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