diff options
author | unknown <sasha@asksasha.com> | 2005-09-14 06:37:52 -0600 |
---|---|---|
committer | unknown <sasha@asksasha.com> | 2005-09-14 06:37:52 -0600 |
commit | 3be8c9074a8f65bfe82ed218b64f989da295f674 (patch) | |
tree | 9429b2253660211c1617ac89d98074c61fe2e785 /sql | |
parent | 02fce1c316e7a33748eb7ccf13a49fbaa2926ee6 (diff) | |
parent | f89424f8b69d50fb26c0af3d226ac20afe2a32da (diff) | |
download | mariadb-git-3be8c9074a8f65bfe82ed218b64f989da295f674.tar.gz |
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
Diffstat (limited to 'sql')
-rw-r--r-- | sql/mysql_priv.h | 2 | ||||
-rw-r--r-- | sql/slave.cc | 9 | ||||
-rw-r--r-- | sql/sql_parse.cc | 50 | ||||
-rw-r--r-- | sql/sql_yacc.yy | 10 |
4 files changed, 46 insertions, 25 deletions
diff --git a/sql/mysql_priv.h b/sql/mysql_priv.h index 0d889aaf0b1..32c5861028e 100644 --- a/sql/mysql_priv.h +++ b/sql/mysql_priv.h @@ -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); diff --git a/sql/slave.cc b/sql/slave.cc index 9ff7a432b89..1be3e3b4a17 100644 --- a/sql/slave.cc +++ b/sql/slave.cc @@ -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 diff --git a/sql/sql_parse.cc b/sql/sql_parse.cc index 131fe3d691d..a2df59e56c7 100644 --- a/sql/sql_parse.cc +++ b/sql/sql_parse.cc @@ -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, diff --git a/sql/sql_yacc.yy b/sql/sql_yacc.yy index 6283cad7cc8..e29aaac8f94 100644 --- a/sql/sql_yacc.yy +++ b/sql/sql_yacc.yy @@ -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 {} ; |