diff options
author | unknown <bell@sanja.is.com.ua> | 2004-03-20 13:36:26 +0200 |
---|---|---|
committer | unknown <bell@sanja.is.com.ua> | 2004-03-20 13:36:26 +0200 |
commit | f379d7b172401206de5654f52466601de874cade (patch) | |
tree | de1ab82158f22c98608b574edb706c1f3de591b5 /sql | |
parent | 647498e9657b7d68faf0cb24bac43a940238920c (diff) | |
download | mariadb-git-f379d7b172401206de5654f52466601de874cade.tar.gz |
after review changes
sql/item.cc:
removed double_fix & already_fixed in Item_field
sql/item.h:
added quick_fix_field() for cases when we are sure that no need full fix_field processing
fixed neg() method for numeric constants to have the same logic as constant parser
Item_null, Item_real, ... are constant which are fixed by creation
sql/item_cmpfunc.h:
right fix_fields in and_conds call
sql/item_func.cc:
changed Item_field constructor call
fix_field emulation call
sql/item_strfunc.cc:
correct layout
sql/item_subselect.cc:
correct layout
changed Item_field constructor call
sql/item_sum.cc:
changed Item_field constructor call
sql/item_sum.h:
changed Item_field constructor call
sql/sql_base.cc:
fixed layout
right fix_fields calls
sql/sql_help.cc:
changed Item_field constructor call
sql/sql_load.cc:
changed Item_field constructor call
sql/sql_parse.cc:
constant changed
sql/sql_select.cc:
fixed layout
fix_field emulation insted of real fix_fields call
sql/sql_show.cc:
changed Item_field constructor call
sql/sql_union.cc:
changed Item_field constructor call
double_fix removed
sql/sql_update.cc:
renamed variable, fixed layout
sql/sql_yacc.yy:
typo fixed
fix_fields emulation calls
hegation of numbers fixed
Diffstat (limited to 'sql')
-rw-r--r-- | sql/item.cc | 35 | ||||
-rw-r--r-- | sql/item.h | 57 | ||||
-rw-r--r-- | sql/item_cmpfunc.h | 4 | ||||
-rw-r--r-- | sql/item_func.cc | 10 | ||||
-rw-r--r-- | sql/item_strfunc.cc | 7 | ||||
-rw-r--r-- | sql/item_subselect.cc | 5 | ||||
-rw-r--r-- | sql/item_sum.cc | 2 | ||||
-rw-r--r-- | sql/item_sum.h | 2 | ||||
-rw-r--r-- | sql/sql_base.cc | 32 | ||||
-rw-r--r-- | sql/sql_help.cc | 6 | ||||
-rw-r--r-- | sql/sql_load.cc | 2 | ||||
-rw-r--r-- | sql/sql_parse.cc | 7 | ||||
-rw-r--r-- | sql/sql_select.cc | 52 | ||||
-rw-r--r-- | sql/sql_show.cc | 2 | ||||
-rw-r--r-- | sql/sql_union.cc | 20 | ||||
-rw-r--r-- | sql/sql_update.cc | 8 | ||||
-rw-r--r-- | sql/sql_yacc.yy | 15 |
17 files changed, 156 insertions, 110 deletions
diff --git a/sql/item.cc b/sql/item.cc index 2a0afe27949..3df40dba5b7 100644 --- a/sql/item.cc +++ b/sql/item.cc @@ -301,15 +301,12 @@ bool DTCollation::aggregate(DTCollation &dt) return 0; } -Item_field::Item_field(Field *f, bool already_fixed) +Item_field::Item_field(Field *f) :Item_ident(NullS, f->table_name, f->field_name) -#ifndef DBUG_OFF - ,double_fix(0) -#endif { set_field(f); collation.set(DERIVATION_IMPLICIT); - fixed= already_fixed; + fixed= 1; } // Constructor need to process subselect with temporary tables (see Item) @@ -317,9 +314,6 @@ Item_field::Item_field(THD *thd, Item_field *item) :Item_ident(thd, item), field(item->field), result_field(item->result_field) -#ifndef DBUG_OFF - ,double_fix(0) -#endif { collation.set(DERIVATION_IMPLICIT); } @@ -487,6 +481,7 @@ Item *Item_field::get_tmp_table_item(THD *thd) String *Item_int::val_str(String *str) { + // following assert is redundant, because fixed=1 assigned in constructor DBUG_ASSERT(fixed == 1); str->set(value, &my_charset_bin); return str; @@ -502,6 +497,7 @@ void Item_int::print(String *str) String *Item_uint::val_str(String *str) { + // following assert is redundant, because fixed=1 assigned in constructor DBUG_ASSERT(fixed == 1); str->set((ulonglong) value, &my_charset_bin); return str; @@ -518,6 +514,7 @@ void Item_uint::print(String *str) String *Item_real::val_str(String *str) { + // following assert is redundant, because fixed=1 assigned in constructor DBUG_ASSERT(fixed == 1); str->set(value,decimals,&my_charset_bin); return str; @@ -537,20 +534,23 @@ bool Item_null::eq(const Item *item, bool binary_cmp) const { return item->type() == type(); } double Item_null::val() { - // NULL can be used without fix_fields + // following assert is redundant, because fixed=1 assigned in constructor + DBUG_ASSERT(fixed == 1); null_value=1; return 0.0; } longlong Item_null::val_int() { - // NULL can be used without fix_fields + // following assert is redundant, because fixed=1 assigned in constructor + DBUG_ASSERT(fixed == 1); null_value=1; return 0; } /* ARGSUSED */ String *Item_null::val_str(String *str) { - // NULL can be used without fix_fields + // following assert is redundant, because fixed=1 assigned in constructor + DBUG_ASSERT(fixed == 1); null_value=1; return 0; } @@ -832,8 +832,7 @@ bool Item::fix_fields(THD *thd, { // We do not check fields which are fixed during construction - DBUG_ASSERT(fixed == 0 || type() == INT_ITEM || type() == CACHE_ITEM || - type() == STRING_ITEM || type() == MYSQL_TYPE_DATETIME); + DBUG_ASSERT(fixed == 0 || basic_const_item()); fixed= 1; return 0; } @@ -904,7 +903,7 @@ static void mark_as_dependent(THD *thd, SELECT_LEX *last, SELECT_LEX *current, bool Item_field::fix_fields(THD *thd, TABLE_LIST *tables, Item **ref) { - DBUG_ASSERT(fixed == 0 || double_fix == 0); + DBUG_ASSERT(fixed == 0); if (!field) // If field is not checked { TABLE_LIST *where= 0; @@ -1341,6 +1340,10 @@ int Item_int::save_in_field(Field *field, bool no_conversions) return field->store(nr); } +Item_num *Item_uint::neg() +{ + return new Item_real(name, - ((double) value), 0, max_length); +} int Item_real::save_in_field(Field *field, bool no_conversions) { @@ -1383,10 +1386,12 @@ Item_varbinary::Item_varbinary(const char *str, uint str_length) } *ptr=0; // Keep purify happy collation.set(&my_charset_bin, DERIVATION_COERCIBLE); + fixed= 1; } longlong Item_varbinary::val_int() { + // following assert is redundant, because fixed=1 assigned in constructor DBUG_ASSERT(fixed == 1); char *end=(char*) str_value.ptr()+str_value.length(), *ptr=end-min(str_value.length(),sizeof(longlong)); @@ -1648,7 +1653,7 @@ bool Item_ref::fix_fields(THD *thd,TABLE_LIST *tables, Item **reference) { ref= 0; // To prevent "delete *ref;" on ~Item_erf() of this item Item_field* fld; - if (!((*reference)= fld= new Item_field(tmp, 1))) + if (!((*reference)= fld= new Item_field(tmp))) return 1; register_item_tree_changing(reference); mark_as_dependent(thd, last, thd->lex->current_select, fld); diff --git a/sql/item.h b/sql/item.h index 6917a5ffef7..5f94320b547 100644 --- a/sql/item.h +++ b/sql/item.h @@ -137,6 +137,11 @@ public: } virtual void make_field(Send_field *field); virtual bool fix_fields(THD *, struct st_table_list *, Item **); + /* + should be used in case where we are shure that we do not need + complete fix_fields() procedure. + */ + inline void quick_fix_field() { fixed= 1; } virtual int save_in_field(Field *field, bool no_conversions); virtual void save_org_in_field(Field *field) { (void) save_in_field(field, 1); } @@ -245,7 +250,7 @@ public: class Item_num: public Item { public: - virtual void neg()= 0; + virtual Item_num* neg()= 0; }; @@ -288,7 +293,7 @@ public: { collation.set(DERIVATION_IMPLICIT); } // Constructor need to process subselect with temporary tables (see Item) Item_field(THD *thd, Item_field *item); - Item_field(Field *field, bool already_fixed); + Item_field(Field *field); enum Type type() const { return FIELD_ITEM; } bool eq(const Item *item, bool binary_cmp) const; double val(); @@ -321,13 +326,19 @@ public: void cleanup(); friend class Item_default_value; friend class Item_insert_value; + friend class st_select_lex_unit; }; class Item_null :public Item { public: Item_null(char *name_par=0) - { maybe_null=null_value=TRUE; name= name_par ? name_par : (char*) "NULL";} + { + maybe_null= null_value= TRUE; + max_length= 0; + name= name_par ? name_par : (char*) "NULL"; + fixed= 1; + } enum Type type() const { return NULL_ITEM; } bool eq(const Item *item, bool binary_cmp) const; double val(); @@ -338,13 +349,8 @@ public: bool send(Protocol *protocol, String *str); enum Item_result result_type () const { return STRING_RESULT; } enum_field_types field_type() const { return MYSQL_TYPE_NULL; } - bool fix_fields(THD *thd, struct st_table_list *list, Item **item) - { - DBUG_ASSERT(fixed == 0); - bool res= Item::fix_fields(thd, list, item); - max_length=0; - return res; - } + // to prevent drop fixed flag (no need parent cleanup call) + void cleanup() {} bool basic_const_item() const { return 1; } Item *new_item() { return new Item_null(name); } bool is_null() { return 1; } @@ -431,9 +437,9 @@ public: bool basic_const_item() const { return 1; } Item *new_item() { return new Item_int(name,value,max_length); } // to prevent drop fixed flag (no need parent cleanup call) - void cleanup() { fixed= 1; } + void cleanup() {} void print(String *str); - void neg() { value= -value; } + Item_num *neg() { value= -value; return this; } }; @@ -451,6 +457,7 @@ public: Item *new_item() { return new Item_uint(name,max_length); } int save_in_field(Field *field, bool no_conversions); void print(String *str); + Item_num *neg (); }; @@ -459,11 +466,12 @@ class Item_real :public Item_num public: double value; // Item_real() :value(0) {} - Item_real(const char *str_arg,uint length) :value(my_atof(str_arg)) + Item_real(const char *str_arg, uint length) :value(my_atof(str_arg)) { name=(char*) str_arg; decimals=(uint8) nr_of_decimals(str_arg); max_length=length; + fixed= 1; } Item_real(const char *str,double val_arg,uint decimal_par,uint length) :value(val_arg) @@ -471,8 +479,9 @@ public: name=(char*) str; decimals=(uint8) decimal_par; max_length=length; + fixed= 1; } - Item_real(double value_par) :value(value_par) {} + Item_real(double value_par) :value(value_par) { fixed= 1; } int save_in_field(Field *field, bool no_conversions); enum Type type() const { return REAL_ITEM; } enum_field_types field_type() const { return MYSQL_TYPE_DOUBLE; } @@ -484,8 +493,10 @@ public: } String *val_str(String*); bool basic_const_item() const { return 1; } + // to prevent drop fixed flag (no need parent cleanup call) + void cleanup() {} Item *new_item() { return new Item_real(name,value,decimals,max_length); } - void neg() { value= -value; } + Item_num *neg() { value= -value; return this; } }; @@ -564,11 +575,8 @@ public: String *const_string() { return &str_value; } inline void append(char *str, uint length) { str_value.append(str, length); } void print(String *str); - void cleanup() - { - // it is constant => can be used without fix_fields (and frequently used) - fixed= 1; - } + // to prevent drop fixed flag (no need parent cleanup call) + void cleanup() {} }; /* for show tables */ @@ -613,10 +621,13 @@ public: double val() { DBUG_ASSERT(fixed == 1); return (double) Item_varbinary::val_int(); } longlong val_int(); + bool basic_const_item() const { return 1; } String *val_str(String*) { DBUG_ASSERT(fixed == 1); return &str_value; } int save_in_field(Field *field, bool no_conversions); enum Item_result result_type () const { return STRING_RESULT; } enum_field_types field_type() const { return MYSQL_TYPE_STRING; } + // to prevent drop fixed flag (no need parent cleanup call) + void cleanup() {} }; @@ -874,7 +885,6 @@ public: bool eq(const Item *item, bool binary_cmp) const; bool fix_fields(THD *, struct st_table_list *, Item **); void print(String *str); - virtual bool basic_const_item() const { return true; } int save_in_field(Field *field_arg, bool no_conversions) { if (!arg) @@ -902,7 +912,6 @@ public: bool eq(const Item *item, bool binary_cmp) const; bool fix_fields(THD *, struct st_table_list *, Item **); void print(String *str); - virtual bool basic_const_item() const { return true; } int save_in_field(Field *field_arg, bool no_conversions) { return Item_field::save_in_field(field_arg, no_conversions); @@ -926,7 +935,7 @@ public: void set_used_tables(table_map map) { used_table_map= map; } - virtual bool allocate(uint i) { return 0; }; + virtual bool allocate(uint i) { return 0; } virtual bool setup(Item *item) { example= item; @@ -941,7 +950,7 @@ public: table_map used_tables() const { return used_table_map; } virtual void keep_array() {} // to prevent drop fixed flag (no need parent cleanup call) - void cleanup() { fixed= 1; } + void cleanup() {} void print(String *str); }; diff --git a/sql/item_cmpfunc.h b/sql/item_cmpfunc.h index a2587f408b1..95520c0c222 100644 --- a/sql/item_cmpfunc.h +++ b/sql/item_cmpfunc.h @@ -991,13 +991,13 @@ public: /* Some usefull inline functions */ -inline Item *and_conds(Item *a,Item *b) +inline Item *and_conds(Item *a, Item *b, TABLE_LIST *tables) { if (!b) return a; if (!a) return b; Item *cond= new Item_cond_and(a,b); if (cond) - cond->fix_fields(current_thd, 0, &cond); + cond->fix_fields(current_thd, tables, &cond); return cond; } diff --git a/sql/item_func.cc b/sql/item_func.cc index be9367ec381..8b516a56b2b 100644 --- a/sql/item_func.cc +++ b/sql/item_func.cc @@ -428,7 +428,7 @@ void Item_func::fix_num_length_and_dec() Item *Item_func::get_tmp_table_item(THD *thd) { if (!with_sum_func && !const_item()) - return new Item_field(result_field, 1); + return new Item_field(result_field); return copy_or_same(thd); } @@ -2780,7 +2780,13 @@ void Item_func_match::init_search(bool no_order) fields.push_back(args[i]); concat=new Item_func_concat_ws(new Item_string(" ",1, cmp_collation.collation), fields); - concat->fix_fields(current_thd, 0, &concat); + /* + Above function used only to get value and do not need fix_fields for it: + Item_string - basic constant + fields - fix_fieds already was called for this arguments + Item_func_concat_ws - do not need fix_fields to produce value + */ + concat->quick_fix_field(); } if (master) diff --git a/sql/item_strfunc.cc b/sql/item_strfunc.cc index 008f54ba20f..a711d9b92b1 100644 --- a/sql/item_strfunc.cc +++ b/sql/item_strfunc.cc @@ -74,9 +74,10 @@ longlong Item_str_func::val_int() int err; String *res; res=val_str(&str_value); - return res ? - my_strntoll(res->charset(), res->ptr(), res->length(), 10, NULL, &err) : - (longlong) 0; + return (res ? + my_strntoll(res->charset(), res->ptr(), res->length(), 10, NULL, + &err) : + (longlong) 0); } diff --git a/sql/item_subselect.cc b/sql/item_subselect.cc index b0f5e3ba9d4..196b54141d1 100644 --- a/sql/item_subselect.cc +++ b/sql/item_subselect.cc @@ -116,6 +116,8 @@ bool Item_subselect::fix_fields(THD *thd_param, TABLE_LIST *tables, Item **ref) { if (substitution) { + int ret= 0; + // did we changed top item of WHERE condition if (unit->outer_select()->where == (*ref)) unit->outer_select()->where= substitution; // correct WHERE for PS @@ -127,7 +129,6 @@ bool Item_subselect::fix_fields(THD *thd_param, TABLE_LIST *tables, Item **ref) substitution= 0; fixed= 1; thd->where= "checking transformed subquery"; - int ret= 0; if (!(*ref)->fixed) ret= (*ref)->fix_fields(thd, tables, ref); // We can't substitute aggregate functions (like (SELECT (max(i))) @@ -204,7 +205,7 @@ bool Item_subselect::const_item() const Item *Item_subselect::get_tmp_table_item(THD *thd) { if (!with_sum_func && !const_item()) - return new Item_field(result_field, 1); + return new Item_field(result_field); return copy_or_same(thd); } diff --git a/sql/item_sum.cc b/sql/item_sum.cc index a8afbbb165e..807585f696d 100644 --- a/sql/item_sum.cc +++ b/sql/item_sum.cc @@ -113,7 +113,7 @@ Item *Item_sum::get_tmp_table_item(THD *thd) if (arg->type() == Item::FIELD_ITEM) ((Item_field*) arg)->field= result_field_tmp++; else - sum_item->args[i]= new Item_field(result_field_tmp++, 1); + sum_item->args[i]= new Item_field(result_field_tmp++); } } } diff --git a/sql/item_sum.h b/sql/item_sum.h index 397d853aa78..1c31f1a9b70 100644 --- a/sql/item_sum.h +++ b/sql/item_sum.h @@ -88,7 +88,7 @@ public: virtual void fix_length_and_dec() { maybe_null=1; null_value=1; } virtual const char *func_name() const { return "?"; } virtual Item *result_item(Field *field) - { return new Item_field(field, 1);} + { return new Item_field(field);} table_map used_tables() const { return ~(table_map) 0; } /* Not used */ bool const_item() const { return 0; } bool is_null() { return null_value; } diff --git a/sql/sql_base.cc b/sql/sql_base.cc index 22249f93320..56857aaa632 100644 --- a/sql/sql_base.cc +++ b/sql/sql_base.cc @@ -2293,7 +2293,7 @@ insert_fields(THD *thd,TABLE_LIST *tables, const char *db_name, thd->used_tables|=table->map; while ((field = *ptr++)) { - Item_field *item= new Item_field(field, 0); + Item_field *item= new Item_field(field); if (!found++) (void) it->replace(item); // Replace '*' else @@ -2365,7 +2365,7 @@ int setup_conds(THD *thd,TABLE_LIST *tables,COND **conds) !(specialflag & SPECIAL_NO_NEW_FUNC))) { table->outer_join= 0; - if (!(*conds=and_conds(*conds, table->on_expr))) + if (!(*conds= and_conds(*conds, table->on_expr, tables))) DBUG_RETURN(1); table->on_expr=0; } @@ -2373,9 +2373,9 @@ int setup_conds(THD *thd,TABLE_LIST *tables,COND **conds) if (table->natural_join) { /* Make a join of all fields with have the same name */ - TABLE *t1=table->table; - TABLE *t2=table->natural_join->table; - Item_cond_and *cond_and=new Item_cond_and(); + TABLE *t1= table->table; + TABLE *t2= table->natural_join->table; + Item_cond_and *cond_and= new Item_cond_and(); if (!cond_and) // If not out of memory DBUG_RETURN(1); cond_and->top_level_item(); @@ -2390,10 +2390,8 @@ int setup_conds(THD *thd,TABLE_LIST *tables,COND **conds) t1->field[i]->field_name, t2->field[j]->field_name)) { - // fix_fields() call will be made for tmp by cond_and->fix_fields - Item_func_eq *tmp=new Item_func_eq(new Item_field(t1->field[i], 1), - new Item_field(t2->field[j], - 1)); + Item_func_eq *tmp= new Item_func_eq(new Item_field(t1->field[i]), + new Item_field(t2->field[j])); if (!tmp) DBUG_RETURN(1); /* Mark field used for table cache */ @@ -2405,18 +2403,22 @@ int setup_conds(THD *thd,TABLE_LIST *tables,COND **conds) } } } - //cond_and->used_tables_cache= t1->map | t2->map; thd->lex->current_select->cond_count+= cond_and->list.elements; - if (cond_and->fix_fields(thd, tables, (Item**)&cond_and) || - cond_and->check_cols(1)) - DBUG_RETURN(1); + if (!table->outer_join) // Not left join { - if (!(*conds=and_conds(*conds, cond_and))) + if (!(*conds= and_conds(*conds, cond_and, tables)) || + (*conds && !(*conds)->fixed && + (*conds)->fix_fields(thd, tables, conds))) DBUG_RETURN(1); } else - table->on_expr=and_conds(table->on_expr,cond_and); + { + table->on_expr= and_conds(table->on_expr, cond_and, tables); + if (table->on_expr && !table->on_expr->fixed && + table->on_expr->fix_fields(thd, tables, &table->on_expr)) + DBUG_RETURN(1); + } } } DBUG_RETURN(test(thd->net.report_error)); diff --git a/sql/sql_help.cc b/sql/sql_help.cc index f3d5775133c..f6bae67c3b6 100644 --- a/sql/sql_help.cc +++ b/sql/sql_help.cc @@ -624,7 +624,7 @@ SQL_SELECT *prepare_select_for_name(THD *thd, const char *mask, uint mlen, TABLE_LIST *tables, TABLE *table, Field *pfname, int *error) { - Item *cond= new Item_func_like(new Item_field(pfname, 1), + Item *cond= new Item_func_like(new Item_field(pfname), new Item_string(mask,mlen,pfname->charset()), (char*) "\\"); if (thd->is_fatal_error) @@ -744,10 +744,10 @@ int mysqld_help(THD *thd, const char *mask) { Field *topic_cat_id= used_fields[help_topic_help_category_id].field; Item *cond_topic_by_cat= - new Item_func_equal(new Item_field(topic_cat_id, 1), + new Item_func_equal(new Item_field(topic_cat_id), new Item_int((int32)category_id)); Item *cond_cat_by_cat= - new Item_func_equal(new Item_field(cat_cat_id, 1), + new Item_func_equal(new Item_field(cat_cat_id), new Item_int((int32)category_id)); if (!(select_topics_by_cat= prepare_simple_select(thd,cond_topic_by_cat, tables,tables[0].table, diff --git a/sql/sql_load.cc b/sql/sql_load.cc index 1ae93f2b1a0..58a9b9c588d 100644 --- a/sql/sql_load.cc +++ b/sql/sql_load.cc @@ -122,7 +122,7 @@ int mysql_load(THD *thd,sql_exchange *ex,TABLE_LIST *table_list, { Field **field; for (field=table->field; *field ; field++) - fields.push_back(new Item_field(*field, 1)); + fields.push_back(new Item_field(*field)); } else { // Part field list diff --git a/sql/sql_parse.cc b/sql/sql_parse.cc index a33f15a1177..43129f7c3f1 100644 --- a/sql/sql_parse.cc +++ b/sql/sql_parse.cc @@ -4031,11 +4031,10 @@ bool add_field_to_list(THD *thd, char *field_name, enum_field_types type, if (default_value) { - if (default_value->fix_fields(thd, 0, &default_value)) - { - DBUG_RETURN(1); - } /* + Default value should be literal => basic constants => + no need fix_fields() + We allow specifying value for first TIMESTAMP column altough it is silently ignored. This should be fixed in 4.1 (by proper warning or real support for default values) diff --git a/sql/sql_select.cc b/sql/sql_select.cc index 171421c1796..020356782ba 100644 --- a/sql/sql_select.cc +++ b/sql/sql_select.cc @@ -321,9 +321,9 @@ JOIN::prepare(Item ***rref_pointer_array, thd->where="having clause"; thd->allow_sum_func=1; select_lex->having_fix_field= 1; - bool having_fix_rc= !having->fixed && - (having->fix_fields(thd, tables_list, &having) || - having->check_cols(1)); + bool having_fix_rc= (!having->fixed && + (having->fix_fields(thd, tables_list, &having) || + having->check_cols(1))); select_lex->having_fix_field= 0; if (having_fix_rc || thd->net.report_error) DBUG_RETURN(-1); /* purecov: inspected */ @@ -525,7 +525,7 @@ JOIN::optimize() } #endif - conds= optimize_cond(thd, conds,&cond_value); + conds= optimize_cond(thd, conds, &cond_value); if (thd->net.report_error) { error= 1; @@ -1431,10 +1431,13 @@ JOIN::exec() { if (!(curr_table->select->cond= new Item_cond_and(curr_table->select->cond, - sort_table_cond)) || - curr_table->select->cond->fix_fields(thd, tables_list, - &curr_table->select->cond)) + sort_table_cond))) DBUG_VOID_RETURN; + /* + Item_cond_and do not need fix_fields for execution, its parameters + are fixed or do not need fix_fields, too + */ + curr_table->select->cond->quick_fix_field(); } curr_table->select_cond= curr_table->select->cond; curr_table->select_cond->top_level_item(); @@ -3533,7 +3536,7 @@ make_join_select(JOIN *join,SQL_SELECT *select,COND *cond) { /* Join with outer join condition */ COND *orig_cond=sel->cond; - sel->cond=and_conds(sel->cond,tab->on_expr); + sel->cond=and_conds(sel->cond, tab->on_expr, 0); if (sel->test_quick_select(join->thd, tab->keys, used_tables & ~ current_map, (join->select_options & @@ -5016,7 +5019,7 @@ create_tmp_table(THD *thd,TMP_TABLE_PARAM *param,List<Item> &fields, *blob_field++= new_field; blob_count++; } - ((Item_sum*) item)->args[i]= new Item_field(new_field, 1); + ((Item_sum*) item)->args[i]= new Item_field(new_field); } } } @@ -6798,8 +6801,14 @@ make_cond_for_table(COND *cond, table_map tables, table_map used_table) case 1: return new_cond->argument_list()->head(); default: - if (new_cond->fix_fields(current_thd, 0, (Item**)&new_cond)) - return (COND*) 0; + /* + Item_cond_and do not need fix_fields for execution, its parameters + are fixed or do not need fix_fields, too + */ + new_cond->quick_fix_field(); + new_cond->used_tables_cache= + ((Item_cond_and*) cond)->used_tables_cache & + tables; return new_cond; } } @@ -6817,8 +6826,12 @@ make_cond_for_table(COND *cond, table_map tables, table_map used_table) return (COND*) 0; // Always true new_cond->argument_list()->push_back(fix); } - if (new_cond->fix_fields(current_thd, 0, (Item**)&new_cond)) - return (COND*) 0; + /* + Item_cond_and do not need fix_fields for execution, its parameters + are fixed or do not need fix_fields, too + */ + new_cond->quick_fix_field(); + new_cond->used_tables_cache= ((Item_cond_or*) cond)->used_tables_cache; new_cond->top_level_item(); return new_cond; } @@ -7324,7 +7337,7 @@ static bool fix_having(JOIN *join, Item **having) else // This should never happen if (!(table->select->cond= new Item_cond_and(table->select->cond, sort_table_cond)) || - table->select->cond->fix_fields(join->thd, join->tanles_list, + table->select->cond->fix_fields(join->thd, join->tables_list, &table->select->cond)) return 1; table->select_cond=table->select->cond; @@ -7945,12 +7958,13 @@ find_order_in_list(THD *thd, Item **ref_pointer_array, order->in_field_list=0; Item *it= *order->item; /* - we check it->fixed because Item_func_group_concat can put - arguments for which fix_fields already was called + We check it->fixed because Item_func_group_concat can put + arguments for which fix_fields already was called. + + 'it' reassigned in if condition because fix_field can change it. */ if (!it->fixed && (it->fix_fields(thd, tables, order->item) || - //'it' ressigned because fix_field can change it (it= *order->item)->check_cols(1) || thd->is_fatal_error)) return 1; // Wrong field @@ -8603,7 +8617,7 @@ change_to_use_tmp_fields(THD *thd, Item **ref_pointer_array, if (item->type() == Item::SUM_FUNC_ITEM && field->table->group) item_field= ((Item_sum*) item)->result_item(field); else - item_field= (Item*) new Item_field(field, 1); + item_field= (Item*) new Item_field(field); if (!item_field) return TRUE; // Fatal error item_field->name= item->name; /*lint -e613 */ @@ -8778,7 +8792,7 @@ static bool add_ref_to_table_cond(THD *thd, JOIN_TAB *join_tab) Field *field=table->field[table->key_info[join_tab->ref.key].key_part[i]. fieldnr-1]; Item *value=join_tab->ref.items[i]; - cond->add(new Item_func_equal(new Item_field(field, 1), value)); + cond->add(new Item_func_equal(new Item_field(field), value)); } if (thd->is_fatal_error) DBUG_RETURN(TRUE); diff --git a/sql/sql_show.cc b/sql/sql_show.cc index 2a94c66ac1a..d68db2cb3bc 100644 --- a/sql/sql_show.cc +++ b/sql/sql_show.cc @@ -1050,7 +1050,7 @@ mysqld_list_fields(THD *thd, TABLE_LIST *table_list, const char *wild) { if (!wild || !wild[0] || !wild_case_compare(system_charset_info, field->field_name,wild)) - field_list.push_back(new Item_field(field, 1)); + field_list.push_back(new Item_field(field)); } restore_record(table,default_values); // Get empty record if (thd->protocol->send_fields(&field_list,2)) diff --git a/sql/sql_union.cc b/sql/sql_union.cc index bb5996919e3..87f70bcbd3a 100644 --- a/sql/sql_union.cc +++ b/sql/sql_union.cc @@ -229,12 +229,9 @@ int st_select_lex_unit::prepare(THD *thd_arg, select_result *sel_result, Field **field; for (field= table->field; *field; field++) { - Item_field *item= new Item_field(*field, 1); - if (item_list.push_back(item)) + Item_field *item= new Item_field(*field); + if (!item || item_list.push_back(item)) DBUG_RETURN(-1); -#ifndef DBUG_OFF - item->double_fix= 0; -#endif } } } @@ -463,4 +460,17 @@ int st_select_lex_unit::cleanup() void st_select_lex_unit::reinit_exec_mechanism() { prepared= optimized= executed= 0; +#ifndef DBUG_OFF + List_iterator_fast<Item> it(item_list); + Item_field *field; + while ((field= (Item_field *)it++)) + { + /* + we can't cleanup here, because it broke link to temporary table field, + but have to drop fixed flag to allow next fix_field of this field + during re-executing + */ + field->fixed= 0; + } +#endif } diff --git a/sql/sql_update.cc b/sql/sql_update.cc index 42dd0895132..6242a03867b 100644 --- a/sql/sql_update.cc +++ b/sql/sql_update.cc @@ -689,7 +689,7 @@ multi_update::initialize_tables(JOIN *join) { TABLE *table=table_ref->table; uint cnt= table_ref->shared; - Item_field *If; + Item_field *ifield; List<Item> temp_fields= *fields_for_table[cnt]; ORDER group; @@ -713,10 +713,10 @@ multi_update::initialize_tables(JOIN *join) /* ok to be on stack as this is not referenced outside of this func */ Field_string offset(table->file->ref_length, 0, "offset", table, &my_charset_bin); - if (!(If= new Item_field(((Field *) &offset), 1))) + if (!(ifield= new Item_field(((Field *) &offset)))) DBUG_RETURN(1); - If->maybe_null=0; - if (temp_fields.push_front(If)) + ifield->maybe_null= 0; + if (temp_fields.push_front(ifield)) DBUG_RETURN(1); /* Make an unique key over the first field to avoid duplicated updates */ diff --git a/sql/sql_yacc.yy b/sql/sql_yacc.yy index 41c5e8f43ad..1fc063a60ee 100644 --- a/sql/sql_yacc.yy +++ b/sql/sql_yacc.yy @@ -4353,10 +4353,10 @@ purge_option: } Item *tmp= new Item_func_unix_timestamp($2); /* - it is OK olny emulate fix_fieds, because we need only + it is OK only emulate fix_fieds, because we need only value of constant */ - tmp->Item::fix_fields(0,0,0); + tmp->quick_fix_field(); Lex->sql_command = SQLCOM_PURGE_BEFORE; Lex->purge_time= (ulong) tmp->val_int(); } @@ -4492,11 +4492,11 @@ text_string: { Item *tmp = new Item_varbinary($1.str,$1.length); /* - it is OK olny emulate fix_fieds, because we need only + it is OK only emulate fix_fieds, because we need only value of constant */ $$= tmp ? - tmp->Item::fix_fields(0,0,0), tmp->val_str((String*) 0) : + tmp->quick_fix_field(), tmp->val_str((String*) 0) : (String*) 0; } ; @@ -4529,9 +4529,8 @@ signed_literal: | '+' NUM_literal { $$ = $2; } | '-' NUM_literal { - $2->neg(); $2->max_length++; - $$= $2; + $$= $2->neg(); } ; @@ -4546,11 +4545,11 @@ literal: { Item *tmp= new Item_varbinary($2.str,$2.length); /* - it is OK olny emulate fix_fieds, because we need only + it is OK only emulate fix_fieds, because we need only value of constant */ String *str= tmp ? - tmp->Item::fix_fields(0,0,0), tmp->val_str((String*) 0) : + tmp->quick_fix_field(), tmp->val_str((String*) 0) : (String*) 0; $$= new Item_string(str ? str->ptr() : "", str ? str->length() : 0, |