summaryrefslogtreecommitdiff
path: root/sql
diff options
context:
space:
mode:
Diffstat (limited to 'sql')
-rw-r--r--sql/item.h16
-rw-r--r--sql/item_func.cc57
-rw-r--r--sql/item_func.h1
-rw-r--r--sql/item_row.cc76
-rw-r--r--sql/item_row.h38
-rw-r--r--sql/item_sum.cc16
-rw-r--r--sql/item_sum.h1
7 files changed, 75 insertions, 130 deletions
diff --git a/sql/item.h b/sql/item.h
index 4b42db2aa9e..314882662ea 100644
--- a/sql/item.h
+++ b/sql/item.h
@@ -3275,6 +3275,16 @@ class Item_args
protected:
Item **args, *tmp_arg[2];
void set_arguments(List<Item> &list);
+ bool walk_args(Item_processor processor, bool walk_subquery, uchar *arg)
+ {
+ for (uint i= 0; i < arg_count; i++)
+ {
+ if (args[i]->walk(processor, walk_subquery, arg))
+ return true;
+ }
+ return false;
+ }
+ bool transform_args(Item_transformer transformer, uchar *arg);
public:
uint arg_count;
Item_args(void)
@@ -3417,6 +3427,12 @@ public:
:Item_result_field(thd, item), Item_args(thd, item) { }
Item_func_or_sum(List<Item> &list)
:Item_result_field(), Item_args(list) { }
+ bool walk(Item_processor processor, bool walk_subquery, uchar *arg)
+ {
+ if (walk_args(processor, walk_subquery, arg))
+ return true;
+ return (this->*processor)(arg);
+ }
/*
This method is used for debug purposes to print the name of an
item to the debug log. The second use of this method is as
diff --git a/sql/item_func.cc b/sql/item_func.cc
index fb4b78df875..ffbc06a1bce 100644
--- a/sql/item_func.cc
+++ b/sql/item_func.cc
@@ -291,21 +291,6 @@ void Item_func::fix_after_pullout(st_select_lex *new_parent, Item **ref)
}
-bool Item_func::walk(Item_processor processor, bool walk_subquery,
- uchar *argument)
-{
- if (arg_count)
- {
- Item **arg,**arg_end;
- for (arg= args, arg_end= args+arg_count; arg != arg_end; arg++)
- {
- if ((*arg)->walk(processor, walk_subquery, argument))
- return 1;
- }
- }
- return (this->*processor)(argument);
-}
-
void Item_func::traverse_cond(Cond_traverser traverser,
void *argument, traverse_order order)
{
@@ -334,6 +319,26 @@ void Item_func::traverse_cond(Cond_traverser traverser,
}
+bool Item_args::transform_args(Item_transformer transformer, uchar *arg)
+{
+ for (uint i= 0; i < arg_count; i++)
+ {
+ Item *new_item= args[i]->transform(transformer, arg);
+ if (!new_item)
+ return true;
+ /*
+ THD::change_item_tree() should be called only if the tree was
+ really transformed, i.e. when a new item has been created.
+ Otherwise we'll be allocating a lot of unnecessary memory for
+ change records at each execution.
+ */
+ if (args[i] != new_item)
+ current_thd->change_item_tree(&args[i], new_item);
+ }
+ return false;
+}
+
+
/**
Transform an Item_func object with a transformer callback function.
@@ -354,26 +359,8 @@ void Item_func::traverse_cond(Cond_traverser traverser,
Item *Item_func::transform(Item_transformer transformer, uchar *argument)
{
DBUG_ASSERT(!current_thd->stmt_arena->is_stmt_prepare());
-
- if (arg_count)
- {
- Item **arg,**arg_end;
- for (arg= args, arg_end= args+arg_count; arg != arg_end; arg++)
- {
- Item *new_item= (*arg)->transform(transformer, argument);
- if (!new_item)
- return 0;
-
- /*
- THD::change_item_tree() should be called only if the tree was
- really transformed, i.e. when a new item has been created.
- Otherwise we'll be allocating a lot of unnecessary memory for
- change records at each execution.
- */
- if (*arg != new_item)
- current_thd->change_item_tree(arg, new_item);
- }
- }
+ if (transform_args(transformer, argument))
+ return 0;
return (this->*transformer)(argument);
}
diff --git a/sql/item_func.h b/sql/item_func.h
index 1b7988ab3cf..eff6b2f3e48 100644
--- a/sql/item_func.h
+++ b/sql/item_func.h
@@ -232,7 +232,6 @@ public:
items, nitems,
item_sep);
}
- bool walk(Item_processor processor, bool walk_subquery, uchar *arg);
Item *transform(Item_transformer transformer, uchar *arg);
Item* compile(Item_analyzer analyzer, uchar **arg_p,
Item_transformer transformer, uchar *arg_t);
diff --git a/sql/item_row.cc b/sql/item_row.cc
index 1fc2000813b..dea26ebc6ae 100644
--- a/sql/item_row.cc
+++ b/sql/item_row.cc
@@ -24,38 +24,6 @@
#include "sql_class.h" // THD, set_var.h: THD
#include "set_var.h"
-/**
- Row items used for comparing rows and IN operations on rows:
-
- @verbatim
- (a, b, c) > (10, 10, 30)
- (a, b, c) = (select c, d, e, from t1 where x=12)
- (a, b, c) IN ((1,2,2), (3,4,5), (6,7,8)
- (a, b, c) IN (select c, d, e, from t1)
- @endverbatim
-
- @todo
- think placing 2-3 component items in item (as it done for function
-*/
-
-Item_row::Item_row(List<Item> &arg):
- Item(), Used_tables_and_const_cache(), not_null_tables_cache(0), with_null(0)
-{
-
- //TODO: think placing 2-3 component items in item (as it done for function)
- if ((arg_count= arg.elements))
- items= (Item**) sql_alloc(sizeof(Item*)*arg_count);
- else
- items= 0;
- List_iterator_fast<Item> li(arg);
- uint i= 0;
- Item *item;
- while ((item= li++))
- {
- items[i]= item;
- i++;
- }
-}
void Item_row::illegal_method_call(const char *method)
{
@@ -72,7 +40,7 @@ bool Item_row::fix_fields(THD *thd, Item **ref)
null_value= 0;
maybe_null= 0;
Item **arg, **arg_end;
- for (arg= items, arg_end= items+arg_count; arg != arg_end ; arg++)
+ for (arg= args, arg_end= args + arg_count; arg != arg_end ; arg++)
{
if (!(*arg)->fixed &&
(*arg)->fix_fields(thd, arg))
@@ -110,7 +78,7 @@ Item_row::eval_not_null_tables(uchar *opt_arg)
not_null_tables_cache= 0;
if (arg_count)
{
- for (arg= items, arg_end= items+arg_count; arg != arg_end ; arg++)
+ for (arg= args, arg_end= args + arg_count; arg != arg_end ; arg++)
{
not_null_tables_cache|= (*arg)->not_null_tables();
}
@@ -136,7 +104,7 @@ void Item_row::split_sum_func(THD *thd, Item **ref_pointer_array,
List<Item> &fields)
{
Item **arg, **arg_end;
- for (arg= items, arg_end= items+arg_count; arg != arg_end ; arg++)
+ for (arg= args, arg_end= args + arg_count; arg != arg_end ; arg++)
(*arg)->split_sum_func2(thd, ref_pointer_array, fields, arg, TRUE);
}
@@ -147,9 +115,9 @@ void Item_row::fix_after_pullout(st_select_lex *new_parent, Item **ref)
not_null_tables_cache= 0;
for (uint i= 0; i < arg_count; i++)
{
- items[i]->fix_after_pullout(new_parent, &items[i]);
- used_tables_and_const_cache_join(items[i]);
- not_null_tables_cache|= items[i]->not_null_tables();
+ args[i]->fix_after_pullout(new_parent, &args[i]);
+ used_tables_and_const_cache_join(args[i]);
+ not_null_tables_cache|= args[i]->not_null_tables();
}
}
@@ -171,47 +139,23 @@ void Item_row::print(String *str, enum_query_type query_type)
{
if (i)
str->append(',');
- items[i]->print(str, query_type);
+ args[i]->print(str, query_type);
}
str->append(')');
}
-bool Item_row::walk(Item_processor processor, bool walk_subquery, uchar *arg)
-{
- for (uint i= 0; i < arg_count; i++)
- {
- if (items[i]->walk(processor, walk_subquery, arg))
- return 1;
- }
- return (this->*processor)(arg);
-}
-
-
Item *Item_row::transform(Item_transformer transformer, uchar *arg)
{
DBUG_ASSERT(!current_thd->stmt_arena->is_stmt_prepare());
- for (uint i= 0; i < arg_count; i++)
- {
- Item *new_item= items[i]->transform(transformer, arg);
- if (!new_item)
- return 0;
-
- /*
- THD::change_item_tree() should be called only if the tree was
- really transformed, i.e. when a new item has been created.
- Otherwise we'll be allocating a lot of unnecessary memory for
- change records at each execution.
- */
- if (items[i] != new_item)
- current_thd->change_item_tree(&items[i], new_item);
- }
+ if (transform_args(transformer, arg))
+ return 0;
return (this->*transformer)(arg);
}
void Item_row::bring_value()
{
for (uint i= 0; i < arg_count; i++)
- items[i]->bring_value();
+ args[i]->bring_value();
}
diff --git a/sql/item_row.h b/sql/item_row.h
index 31efc015909..1bec6212715 100644
--- a/sql/item_row.h
+++ b/sql/item_row.h
@@ -17,20 +17,31 @@
along with this program; if not, write to the Free Software
Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA */
-class Item_row: public Item, private Used_tables_and_const_cache
+/**
+ Row items used for comparing rows and IN operations on rows:
+
+ @verbatim
+ (a, b, c) > (10, 10, 30)
+ (a, b, c) = (select c, d, e, from t1 where x=12)
+ (a, b, c) IN ((1,2,2), (3,4,5), (6,7,8)
+ (a, b, c) IN (select c, d, e, from t1)
+ @endverbatim
+*/
+
+class Item_row: public Item,
+ private Item_args,
+ private Used_tables_and_const_cache
{
- Item **items;
table_map not_null_tables_cache;
- uint arg_count;
bool with_null;
public:
- Item_row(List<Item> &);
+ Item_row(List<Item> &list)
+ :Item_args(list), not_null_tables_cache(0), with_null(0)
+ { }
Item_row(Item_row *item):
- Item(),
+ Item_args(item),
Used_tables_and_const_cache(item),
- items(item->items),
not_null_tables_cache(0),
- arg_count(item->arg_count),
with_null(0)
{}
@@ -72,18 +83,23 @@ public:
void update_used_tables()
{
used_tables_and_const_cache_init();
- used_tables_and_const_cache_update_and_join(arg_count, items);
+ used_tables_and_const_cache_update_and_join(arg_count, args);
}
table_map not_null_tables() const { return not_null_tables_cache; }
virtual void print(String *str, enum_query_type query_type);
- bool walk(Item_processor processor, bool walk_subquery, uchar *arg);
+ bool walk(Item_processor processor, bool walk_subquery, uchar *arg)
+ {
+ if (walk_args(processor, walk_subquery, arg))
+ return true;
+ return (this->*processor)(arg);
+ }
Item *transform(Item_transformer transformer, uchar *arg);
bool eval_not_null_tables(uchar *opt_arg);
uint cols() { return arg_count; }
- Item* element_index(uint i) { return items[i]; }
- Item** addr(uint i) { return items + i; }
+ Item* element_index(uint i) { return args[i]; }
+ Item** addr(uint i) { return args + i; }
bool check_cols(uint c);
bool null_inside() { return with_null; };
void bring_value();
diff --git a/sql/item_sum.cc b/sql/item_sum.cc
index 6b00316849e..bac5c599561 100644
--- a/sql/item_sum.cc
+++ b/sql/item_sum.cc
@@ -497,22 +497,6 @@ Item *Item_sum::get_tmp_table_item(THD *thd)
}
-bool Item_sum::walk (Item_processor processor, bool walk_subquery,
- uchar *argument)
-{
- if (arg_count)
- {
- Item **arg,**arg_end;
- for (arg= args, arg_end= args+arg_count; arg != arg_end; arg++)
- {
- if ((*arg)->walk(processor, walk_subquery, argument))
- return 1;
- }
- }
- return (this->*processor)(argument);
-}
-
-
Field *Item_sum::create_tmp_field(bool group, TABLE *table,
uint convert_blob_length)
{
diff --git a/sql/item_sum.h b/sql/item_sum.h
index 8435924e62d..db45a336b46 100644
--- a/sql/item_sum.h
+++ b/sql/item_sum.h
@@ -476,7 +476,6 @@ public:
Item *get_tmp_table_item(THD *thd);
virtual Field *create_tmp_field(bool group, TABLE *table,
uint convert_blob_length);
- bool walk(Item_processor processor, bool walk_subquery, uchar *argument);
virtual bool collect_outer_ref_processor(uchar *param);
bool init_sum_func_check(THD *thd);
bool check_sum_func(THD *thd, Item **ref);