summaryrefslogtreecommitdiff
path: root/sql/item_func.h
diff options
context:
space:
mode:
Diffstat (limited to 'sql/item_func.h')
-rw-r--r--sql/item_func.h162
1 files changed, 125 insertions, 37 deletions
diff --git a/sql/item_func.h b/sql/item_func.h
index 68a64fef3cb..8d4b507fe28 100644
--- a/sql/item_func.h
+++ b/sql/item_func.h
@@ -44,7 +44,14 @@ protected:
String *val_str_from_val_str_ascii(String *str, String *str2);
public:
uint arg_count;
- table_map used_tables_cache, not_null_tables_cache;
+ /*
+ In some cases used_tables_cache is not what used_tables() return
+ so the method should be used where one need used tables bit map
+ (even internally in Item_func_* code).
+ */
+ table_map used_tables_cache;
+ table_map not_null_tables_cache;
+
bool const_item_cache;
enum Functype { UNKNOWN_FUNC,EQ_FUNC,EQUAL_FUNC,NE_FUNC,LT_FUNC,LE_FUNC,
GE_FUNC,GT_FUNC,FT_FUNC,
@@ -150,13 +157,16 @@ public:
void print_op(String *str, enum_query_type query_type);
void print_args(String *str, uint from, enum_query_type query_type);
virtual void fix_num_length_and_dec();
- void count_only_length();
+ void count_only_length(Item **item, uint nitems);
void count_real_length();
void count_decimal_length();
inline bool get_arg0_date(MYSQL_TIME *ltime, ulonglong fuzzy_date)
{
return (null_value=args[0]->get_date(ltime, fuzzy_date));
}
+ void count_datetime_length(Item **item, uint nitems);
+ bool count_string_result_length(enum_field_types field_type,
+ Item **item, uint nitems);
inline bool get_arg0_time(MYSQL_TIME *ltime)
{
return (null_value=args[0]->get_time(ltime));
@@ -411,38 +421,33 @@ public:
};
-class Item_func_numhybrid: public Item_func
+class Item_func_hybrid_result_type: public Item_func
{
protected:
- Item_result hybrid_type;
+ Item_result cached_result_type;
+
public:
- Item_func_numhybrid() :Item_func(), hybrid_type(REAL_RESULT)
- {}
- Item_func_numhybrid(Item *a) :Item_func(a), hybrid_type(REAL_RESULT)
+ Item_func_hybrid_result_type() :Item_func(), cached_result_type(REAL_RESULT)
{ collation.set_numeric(); }
- Item_func_numhybrid(Item *a,Item *b)
- :Item_func(a,b), hybrid_type(REAL_RESULT)
+ Item_func_hybrid_result_type(Item *a) :Item_func(a), cached_result_type(REAL_RESULT)
{ collation.set_numeric(); }
- Item_func_numhybrid(List<Item> &list)
- :Item_func(list), hybrid_type(REAL_RESULT)
+ Item_func_hybrid_result_type(Item *a,Item *b)
+ :Item_func(a,b), cached_result_type(REAL_RESULT)
+ { collation.set_numeric(); }
+ Item_func_hybrid_result_type(Item *a,Item *b,Item *c)
+ :Item_func(a,b,c), cached_result_type(REAL_RESULT)
+ { collation.set_numeric(); }
+ Item_func_hybrid_result_type(List<Item> &list)
+ :Item_func(list), cached_result_type(REAL_RESULT)
{ collation.set_numeric(); }
- enum Item_result result_type () const { return hybrid_type; }
- void fix_length_and_dec();
- void fix_num_length_and_dec();
- virtual void find_num_type()= 0; /* To be called from fix_length_and_dec */
-
- inline void fix_decimals()
- {
- DBUG_ASSERT(result_type() == DECIMAL_RESULT);
- if (decimals == NOT_FIXED_DEC)
- set_if_smaller(decimals, max_length - 1);
- }
+ enum Item_result result_type () const { return cached_result_type; }
double val_real();
longlong val_int();
my_decimal *val_decimal(my_decimal *);
String *val_str(String*str);
+ bool get_date(MYSQL_TIME *res, ulonglong fuzzy_date);
/**
@brief Performs the operation that this functions implements when the
@@ -479,9 +484,75 @@ public:
@return The result of the operation.
*/
virtual String *str_op(String *)= 0;
- bool is_null() { update_null_value(); return null_value; }
+
+ /**
+ @brief Performs the operation that this functions implements when
+ field type is a temporal type.
+ @return The result of the operation.
+ */
+ virtual bool date_op(MYSQL_TIME *res, uint fuzzy_date)= 0;
+
+};
+
+
+
+class Item_func_hybrid_field_type :public Item_func_hybrid_result_type
+{
+protected:
+ enum_field_types cached_field_type;
+public:
+ Item_func_hybrid_field_type()
+ :Item_func_hybrid_result_type(), cached_field_type(MYSQL_TYPE_DOUBLE)
+ {}
+ Item_func_hybrid_field_type(Item *a, Item *b)
+ :Item_func_hybrid_result_type(a, b), cached_field_type(MYSQL_TYPE_DOUBLE)
+ {}
+ Item_func_hybrid_field_type(Item *a, Item *b, Item *c)
+ :Item_func_hybrid_result_type(a, b, c),
+ cached_field_type(MYSQL_TYPE_DOUBLE)
+ {}
+ Item_func_hybrid_field_type(List<Item> &list)
+ :Item_func_hybrid_result_type(list),
+ cached_field_type(MYSQL_TYPE_DOUBLE)
+ {}
+ enum_field_types field_type() const { return cached_field_type; }
+};
+
+
+
+class Item_func_numhybrid: public Item_func_hybrid_result_type
+{
+protected:
+
+ inline void fix_decimals()
+ {
+ DBUG_ASSERT(result_type() == DECIMAL_RESULT);
+ if (decimals == NOT_FIXED_DEC)
+ set_if_smaller(decimals, max_length - 1);
+ }
+
+public:
+ Item_func_numhybrid() :Item_func_hybrid_result_type()
+ { }
+ Item_func_numhybrid(Item *a) :Item_func_hybrid_result_type(a)
+ { }
+ Item_func_numhybrid(Item *a,Item *b)
+ :Item_func_hybrid_result_type(a,b)
+ { }
+ Item_func_numhybrid(Item *a,Item *b,Item *c)
+ :Item_func_hybrid_result_type(a,b,c)
+ { }
+ Item_func_numhybrid(List<Item> &list)
+ :Item_func_hybrid_result_type(list)
+ { }
+ void fix_length_and_dec();
+ void fix_num_length_and_dec();
+ virtual void find_num_type()= 0; /* To be called from fix_length_and_dec */
+ String *str_op(String *str) { DBUG_ASSERT(0); return 0; }
+ bool date_op(MYSQL_TIME *ltime, uint fuzzydate) { DBUG_ASSERT(0); return true; }
};
+
/* function where type of result detected by first argument */
class Item_func_num1: public Item_func_numhybrid
{
@@ -491,7 +562,6 @@ public:
void fix_num_length_and_dec();
void find_num_type();
- String *str_op(String *str) { DBUG_ASSERT(0); return 0; }
};
@@ -508,7 +578,6 @@ class Item_num_op :public Item_func_numhybrid
}
void find_num_type();
- String *str_op(String *str) { DBUG_ASSERT(0); return 0; }
};
@@ -1270,11 +1339,11 @@ public:
Item_func_sleep(Item *a) :Item_int_func(a) {}
bool const_item() const { return 0; }
const char *func_name() const { return "sleep"; }
- void update_used_tables()
+ table_map used_tables() const
{
- Item_int_func::update_used_tables();
- used_tables_cache|= RAND_TABLE_BIT;
+ return Item_int_func::used_tables() | RAND_TABLE_BIT;
}
+ bool is_expensive() { return 1; }
longlong val_int();
bool check_vcol_func_processor(uchar *int_arg)
{
@@ -1524,6 +1593,12 @@ class Item_func_get_lock :public Item_int_func
longlong val_int();
const char *func_name() const { return "get_lock"; }
void fix_length_and_dec() { max_length=1; set_persist_maybe_null(1);}
+ table_map used_tables() const
+ {
+ return Item_int_func::used_tables() | RAND_TABLE_BIT;
+ }
+ bool const_item() const { return 0; }
+ bool is_expensive() { return 1; }
bool check_vcol_func_processor(uchar *int_arg)
{
return trace_unsupported_by_check_vcol_func_processor(func_name());
@@ -1538,6 +1613,12 @@ public:
longlong val_int();
const char *func_name() const { return "release_lock"; }
void fix_length_and_dec() { max_length=1; set_persist_maybe_null(1);}
+ table_map used_tables() const
+ {
+ return Item_int_func::used_tables() | RAND_TABLE_BIT;
+ }
+ bool const_item() const { return 0; }
+ bool is_expensive() { return 1; }
bool check_vcol_func_processor(uchar *int_arg)
{
return trace_unsupported_by_check_vcol_func_processor(func_name());
@@ -1600,15 +1681,14 @@ public:
:Item_func(b), cached_result_type(INT_RESULT),
entry(NULL), entry_thread_id(0), name(a)
{}
- Item_func_set_user_var(Item_func_set_user_var *item)
- :Item_func(item), cached_result_type(item->cached_result_type),
- entry(item->entry), entry_thread_id(item->entry_thread_id),
- value(item->value), decimal_buff(item->decimal_buff),
- null_item(item->null_item), save_result(item->save_result),
- name(item->name)
- {
- //fixed= 1;
- }
+ Item_func_set_user_var(THD *thd, Item_func_set_user_var *item)
+ :Item_func(thd, item), cached_result_type(item->cached_result_type),
+ entry(item->entry), entry_thread_id(item->entry_thread_id),
+ value(item->value), decimal_buff(item->decimal_buff),
+ null_item(item->null_item), save_result(item->save_result),
+ name(item->name)
+ {}
+
enum Functype functype() const { return SUSERVAR_FUNC; }
double val_real();
longlong val_int();
@@ -1630,6 +1710,12 @@ public:
enum Item_result result_type () const { return cached_result_type; }
bool fix_fields(THD *thd, Item **ref);
void fix_length_and_dec();
+ table_map used_tables() const
+ {
+ return Item_func::used_tables() | RAND_TABLE_BIT;
+ }
+ bool const_item() const { return 0; }
+ bool is_expensive() { return 1; }
virtual void print(String *str, enum_query_type query_type);
void print_as_stmt(String *str, enum_query_type query_type);
const char *func_name() const { return "set_user_var"; }
@@ -1749,6 +1835,8 @@ public:
double val_real();
longlong val_int();
String* val_str(String*);
+ my_decimal *val_decimal(my_decimal *dec_buf)
+ { return val_decimal_from_real(dec_buf); }
/* TODO: fix to support views */
const char *func_name() const { return "get_system_var"; }
/**