mirror of
https://github.com/MariaDB/server.git
synced 2025-07-30 16:24:05 +03:00
Merge spachev@bk-internal.mysql.com:/home/bk/mysql-4.1
into asksasha.com:/reiser-data/mysql-dev/mysql-4.1-bug11139 sql/sql_parse.cc: Auto merged
This commit is contained in:
@ -4,6 +4,26 @@ reset master;
|
||||
reset slave;
|
||||
drop table if exists t1,t2,t3,t4,t5,t6,t7,t8,t9;
|
||||
start slave;
|
||||
set sql_log_bin=0;
|
||||
create database mysqltest_from;
|
||||
set sql_log_bin=1;
|
||||
create database mysqltest_to;
|
||||
use mysqltest_from;
|
||||
drop table if exists a;
|
||||
CREATE TABLE a (i INT);
|
||||
INSERT INTO a VALUES(1);
|
||||
DELETE alias FROM a alias WHERE alias.i=1;
|
||||
SELECT * FROM a;
|
||||
i
|
||||
insert into a values(2),(3);
|
||||
delete a alias FROM a alias where alias.i=2;
|
||||
select * from a;
|
||||
i
|
||||
3
|
||||
use mysqltest_to;
|
||||
select * from a;
|
||||
i
|
||||
3
|
||||
create table t1 (a int);
|
||||
create table t2 (a int);
|
||||
insert into t1 values (1);
|
||||
@ -15,7 +35,10 @@ select * from t2;
|
||||
a
|
||||
1
|
||||
select * from t1;
|
||||
ERROR 42S02: Table 'test.t1' doesn't exist
|
||||
ERROR 42S02: Table 'mysqltest_to.t1' doesn't exist
|
||||
select * from t2;
|
||||
ERROR 42S02: Table 'test.t2' doesn't exist
|
||||
drop table t1,t2;
|
||||
ERROR 42S02: Table 'mysqltest_to.t2' doesn't exist
|
||||
set sql_log_bin=0;
|
||||
drop database mysqltest_from;
|
||||
set sql_log_bin=1;
|
||||
drop database mysqltest_to;
|
||||
|
@ -1 +1 @@
|
||||
--replicate-wild-ignore-table=test.%
|
||||
"--replicate-rewrite-db=mysqltest_from->mysqltest_to" --replicate-do-table=mysqltest_to.a
|
||||
|
@ -1,4 +1,41 @@
|
||||
#multi delete replication bugs
|
||||
|
||||
|
||||
source include/master-slave.inc;
|
||||
|
||||
#BUG#11139 - improper wild-table and table rules
|
||||
#checking for multi deletes with an alias
|
||||
|
||||
connection master;
|
||||
set sql_log_bin=0;
|
||||
create database mysqltest_from;
|
||||
set sql_log_bin=1;
|
||||
|
||||
connection slave;
|
||||
create database mysqltest_to;
|
||||
|
||||
|
||||
connection master;
|
||||
use mysqltest_from;
|
||||
--disable_warnings
|
||||
drop table if exists a;
|
||||
--enable_warnings
|
||||
CREATE TABLE a (i INT);
|
||||
INSERT INTO a VALUES(1);
|
||||
DELETE alias FROM a alias WHERE alias.i=1;
|
||||
SELECT * FROM a;
|
||||
insert into a values(2),(3);
|
||||
delete a alias FROM a alias where alias.i=2;
|
||||
select * from a;
|
||||
save_master_pos;
|
||||
connection slave;
|
||||
|
||||
use mysqltest_to;
|
||||
sync_with_master;
|
||||
select * from a;
|
||||
|
||||
# BUG#3461
|
||||
connection master;
|
||||
create table t1 (a int);
|
||||
create table t2 (a int);
|
||||
|
||||
@ -19,7 +56,13 @@ select * from t1;
|
||||
error 1146;
|
||||
select * from t2;
|
||||
|
||||
# cleanup
|
||||
connection master;
|
||||
drop table t1,t2;
|
||||
set sql_log_bin=0;
|
||||
drop database mysqltest_from;
|
||||
set sql_log_bin=1;
|
||||
connection slave;
|
||||
drop database mysqltest_to;
|
||||
|
||||
# End of 4.1 tests
|
||||
|
||||
|
@ -59,6 +59,7 @@ void kill_one_thread(THD *thd, ulong id);
|
||||
bool net_request_file(NET* net, const char* fname);
|
||||
char* query_table_status(THD *thd,const char *db,const char *table_name);
|
||||
|
||||
|
||||
#define x_free(A) { my_free((gptr) (A),MYF(MY_WME | MY_FAE | MY_ALLOW_ZERO_PTR)); }
|
||||
#define safeFree(x) { if(x) { my_free((gptr) x,MYF(0)); x = NULL; } }
|
||||
#define PREV_BITS(type,A) ((type) (((type) 1 << (A)) -1))
|
||||
@ -464,6 +465,7 @@ void mysql_reset_thd_for_next_command(THD *thd);
|
||||
bool mysql_new_select(LEX *lex, bool move_down);
|
||||
void create_select_for_variable(const char *var_name);
|
||||
void mysql_init_multi_delete(LEX *lex);
|
||||
void fix_multi_delete_lex(LEX* lex);
|
||||
void init_max_user_conn(void);
|
||||
void init_update_queries(void);
|
||||
void free_max_user_conn(void);
|
||||
|
@ -746,14 +746,7 @@ static TABLE_RULE_ENT* find_wild(DYNAMIC_ARRAY *a, const char* key, int len)
|
||||
rules (see code below). For that reason, users should not set conflicting
|
||||
rules because they may get unpredicted results (precedence order is
|
||||
explained in the manual).
|
||||
If no table of the list is marked "updating" (so far this can only happen
|
||||
if the statement is a multi-delete (SQLCOM_DELETE_MULTI) and the "tables"
|
||||
is the tables in the FROM): then we always return 0, because there is no
|
||||
reason we play this statement on this slave if it updates nothing. In the
|
||||
case of SQLCOM_DELETE_MULTI, there will be a second call to tables_ok(),
|
||||
with tables having "updating==TRUE" (those after the DELETE), so this
|
||||
second call will make the decision (because
|
||||
all_tables_not_ok() = !tables_ok(1st_list) && !tables_ok(2nd_list)).
|
||||
|
||||
|
||||
RETURN VALUES
|
||||
0 should not be logged/replicated
|
||||
|
@ -59,6 +59,9 @@ static void remove_escape(char *name);
|
||||
static void refresh_status(void);
|
||||
static bool append_file_to_dir(THD *thd, const char **filename_ptr,
|
||||
const char *table_name);
|
||||
|
||||
static TABLE_LIST* get_table_by_alias(TABLE_LIST* tl, const char* db,
|
||||
const char* alias);
|
||||
|
||||
const char *any_db="*any*"; // Special symbol for check_access
|
||||
|
||||
@ -125,10 +128,7 @@ static bool end_active_trans(THD *thd)
|
||||
*/
|
||||
inline bool all_tables_not_ok(THD *thd, TABLE_LIST *tables)
|
||||
{
|
||||
return (table_rules_on && tables && !tables_ok(thd,tables) &&
|
||||
((thd->lex->sql_command != SQLCOM_DELETE_MULTI) ||
|
||||
!tables_ok(thd,
|
||||
(TABLE_LIST *)thd->lex->auxilliary_table_list.first)));
|
||||
return (table_rules_on && tables && !tables_ok(thd,tables));
|
||||
}
|
||||
#endif
|
||||
|
||||
@ -4245,6 +4245,40 @@ void create_select_for_variable(const char *var_name)
|
||||
DBUG_VOID_RETURN;
|
||||
}
|
||||
|
||||
static TABLE_LIST* get_table_by_alias(TABLE_LIST* tl, const char* db,
|
||||
const char* alias)
|
||||
{
|
||||
for (;tl;tl= tl->next)
|
||||
{
|
||||
if (!strcmp(db,tl->db) &&
|
||||
tl->alias && !my_strcasecmp(table_alias_charset,tl->alias,alias))
|
||||
return tl;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* Sets up lex->auxilliary_table_list */
|
||||
void fix_multi_delete_lex(LEX* lex)
|
||||
{
|
||||
TABLE_LIST *tl;
|
||||
TABLE_LIST *good_list= (TABLE_LIST*)lex->select_lex.table_list.first;
|
||||
|
||||
for (tl= (TABLE_LIST*)lex->auxilliary_table_list.first; tl; tl= tl->next)
|
||||
{
|
||||
TABLE_LIST* good_table= get_table_by_alias(good_list,tl->db,tl->alias);
|
||||
if (good_table && !good_table->derived)
|
||||
{
|
||||
/*
|
||||
real_name points to a member of Table_ident which is
|
||||
allocated via thd->strmake() from THD memroot
|
||||
*/
|
||||
tl->real_name= good_table->real_name;
|
||||
tl->real_name_length= good_table->real_name_length;
|
||||
good_table->updating= tl->updating;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void mysql_init_multi_delete(LEX *lex)
|
||||
{
|
||||
@ -5567,13 +5601,7 @@ int multi_delete_precheck(THD *thd, TABLE_LIST *tables, uint *table_count)
|
||||
(*table_count)++;
|
||||
/* All tables in aux_tables must be found in FROM PART */
|
||||
TABLE_LIST *walk;
|
||||
for (walk= delete_tables; walk; walk= walk->next)
|
||||
{
|
||||
if (!my_strcasecmp(table_alias_charset,
|
||||
target_tbl->alias, walk->alias) &&
|
||||
!strcmp(walk->db, target_tbl->db))
|
||||
break;
|
||||
}
|
||||
walk= get_table_by_alias(delete_tables,target_tbl->db,target_tbl->alias);
|
||||
if (!walk)
|
||||
{
|
||||
my_error(ER_UNKNOWN_TABLE, MYF(0), target_tbl->real_name,
|
||||
|
@ -4295,12 +4295,10 @@ single_multi:
|
||||
}
|
||||
where_clause opt_order_clause
|
||||
delete_limit_clause {}
|
||||
| table_wild_list
|
||||
{ mysql_init_multi_delete(Lex); }
|
||||
FROM join_table_list where_clause
|
||||
| FROM table_wild_list
|
||||
{ mysql_init_multi_delete(Lex); }
|
||||
USING join_table_list where_clause
|
||||
| table_wild_list {mysql_init_multi_delete(Lex);}
|
||||
FROM join_table_list {fix_multi_delete_lex(Lex);} where_clause
|
||||
| FROM table_wild_list { mysql_init_multi_delete(Lex);}
|
||||
USING join_table_list {fix_multi_delete_lex(Lex);} where_clause
|
||||
{}
|
||||
;
|
||||
|
||||
|
Reference in New Issue
Block a user