mirror of
https://github.com/MariaDB/server.git
synced 2025-08-08 11:22:35 +03:00
Manual merge from mysql-trunk-merge.
Conflicts: - extra/comp_err.c - mysql-test/collections/default.experimental - mysql-test/r/archive.result - mysql-test/r/select.result - mysql-test/suite/binlog/r/binlog_unsafe.result - mysql-test/suite/binlog/t/binlog_unsafe.test - mysql-test/suite/rpl/t/disabled.def - mysql-test/t/archive.test - mysql-test/t/select.test - sql/item.cc - sql/item.h - sql/item_timefunc.cc - sql/sql_base.cc - sql/sql_delete.cc - sql/sql_load.cc - sql/sql_partition.cc - sql/sql_table.cc - storage/innobase/handler/ha_innodb.cc - vio/vio.c
This commit is contained in:
@@ -30,6 +30,9 @@
|
||||
#include "sql_select.h"
|
||||
|
||||
static bool convert_constant_item(THD *, Item_field *, Item **);
|
||||
static longlong
|
||||
get_year_value(THD *thd, Item ***item_arg, Item **cache_arg,
|
||||
Item *warn_item, bool *is_null);
|
||||
|
||||
static Item_result item_store_type(Item_result a, Item *item,
|
||||
my_bool unsigned_flag)
|
||||
@@ -533,11 +536,12 @@ void Item_bool_func2::fix_length_and_dec()
|
||||
}
|
||||
|
||||
|
||||
int Arg_comparator::set_compare_func(Item_bool_func2 *item, Item_result type)
|
||||
int Arg_comparator::set_compare_func(Item_result_field *item, Item_result type)
|
||||
{
|
||||
owner= item;
|
||||
func= comparator_matrix[type]
|
||||
[test(owner->functype() == Item_func::EQUAL_FUNC)];
|
||||
[is_owner_equal_func()];
|
||||
|
||||
switch (type) {
|
||||
case ROW_RESULT:
|
||||
{
|
||||
@@ -557,7 +561,8 @@ int Arg_comparator::set_compare_func(Item_bool_func2 *item, Item_result type)
|
||||
my_error(ER_OPERAND_COLUMNS, MYF(0), (*a)->element_index(i)->cols());
|
||||
return 1;
|
||||
}
|
||||
if (comparators[i].set_cmp_func(owner, (*a)->addr(i), (*b)->addr(i)))
|
||||
if (comparators[i].set_cmp_func(owner, (*a)->addr(i), (*b)->addr(i),
|
||||
set_null))
|
||||
return 1;
|
||||
}
|
||||
break;
|
||||
@@ -571,7 +576,8 @@ int Arg_comparator::set_compare_func(Item_bool_func2 *item, Item_result type)
|
||||
if (cmp_collation.set((*a)->collation, (*b)->collation) ||
|
||||
cmp_collation.derivation == DERIVATION_NONE)
|
||||
{
|
||||
my_coll_agg_error((*a)->collation, (*b)->collation, owner->func_name());
|
||||
my_coll_agg_error((*a)->collation, (*b)->collation,
|
||||
owner->func_name());
|
||||
return 1;
|
||||
}
|
||||
if (cmp_collation.collation == &my_charset_bin)
|
||||
@@ -785,15 +791,21 @@ Arg_comparator::can_compare_as_dates(Item *a, Item *b, ulonglong *const_value)
|
||||
|
||||
if (cmp_type != CMP_DATE_DFLT)
|
||||
{
|
||||
THD *thd= current_thd;
|
||||
/*
|
||||
Do not cache GET_USER_VAR() function as its const_item() may return TRUE
|
||||
for the current thread but it still may change during the execution.
|
||||
Don't use cache while in the context analysis mode only (i.e. for
|
||||
EXPLAIN/CREATE VIEW and similar queries). Cache is useless in such
|
||||
cases and can cause problems. For example evaluating subqueries can
|
||||
confuse storage engines since in context analysis mode tables
|
||||
aren't locked.
|
||||
*/
|
||||
if (cmp_type != CMP_DATE_WITH_DATE && str_arg->const_item() &&
|
||||
if (!thd->is_context_analysis_only() &&
|
||||
cmp_type != CMP_DATE_WITH_DATE && str_arg->const_item() &&
|
||||
(str_arg->type() != Item::FUNC_ITEM ||
|
||||
((Item_func*)str_arg)->functype() != Item_func::GUSERVAR_FUNC))
|
||||
{
|
||||
THD *thd= current_thd;
|
||||
ulonglong value;
|
||||
bool error;
|
||||
String tmp, *str_val= 0;
|
||||
@@ -876,7 +888,7 @@ get_time_value(THD *thd, Item ***item_arg, Item **cache_arg,
|
||||
}
|
||||
|
||||
|
||||
int Arg_comparator::set_cmp_func(Item_bool_func2 *owner_arg,
|
||||
int Arg_comparator::set_cmp_func(Item_result_field *owner_arg,
|
||||
Item **a1, Item **a2,
|
||||
Item_result type)
|
||||
{
|
||||
@@ -886,6 +898,8 @@ int Arg_comparator::set_cmp_func(Item_bool_func2 *owner_arg,
|
||||
owner= owner_arg;
|
||||
a= a1;
|
||||
b= a2;
|
||||
owner= owner_arg;
|
||||
thd= current_thd;
|
||||
|
||||
if ((cmp_type= can_compare_as_dates(*a, *b, &const_value)))
|
||||
{
|
||||
@@ -916,9 +930,10 @@ int Arg_comparator::set_cmp_func(Item_bool_func2 *owner_arg,
|
||||
b= (Item **)&b_cache;
|
||||
}
|
||||
}
|
||||
is_nulls_eq= test(owner && owner->functype() == Item_func::EQUAL_FUNC);
|
||||
is_nulls_eq= is_owner_equal_func();
|
||||
func= &Arg_comparator::compare_datetime;
|
||||
get_value_func= &get_datetime_value;
|
||||
get_value_a_func= &get_datetime_value;
|
||||
get_value_b_func= &get_datetime_value;
|
||||
return 0;
|
||||
}
|
||||
else if (type == STRING_RESULT && (*a)->field_type() == MYSQL_TYPE_TIME &&
|
||||
@@ -927,9 +942,10 @@ int Arg_comparator::set_cmp_func(Item_bool_func2 *owner_arg,
|
||||
/* Compare TIME values as integers. */
|
||||
a_cache= 0;
|
||||
b_cache= 0;
|
||||
is_nulls_eq= test(owner && owner->functype() == Item_func::EQUAL_FUNC);
|
||||
is_nulls_eq= is_owner_equal_func();
|
||||
func= &Arg_comparator::compare_datetime;
|
||||
get_value_func= &get_time_value;
|
||||
get_value_a_func= &get_time_value;
|
||||
get_value_b_func= &get_time_value;
|
||||
return 0;
|
||||
}
|
||||
else if (type == STRING_RESULT &&
|
||||
@@ -938,9 +954,42 @@ int Arg_comparator::set_cmp_func(Item_bool_func2 *owner_arg,
|
||||
{
|
||||
DTCollation coll;
|
||||
coll.set((*a)->collation.collation);
|
||||
if (agg_item_set_converter(coll, owner_arg->func_name(),
|
||||
if (agg_item_set_converter(coll, owner->func_name(),
|
||||
b, 1, MY_COLL_CMP_CONV, 1))
|
||||
return 1;
|
||||
} else if (type != ROW_RESULT && ((*a)->field_type() == MYSQL_TYPE_YEAR ||
|
||||
(*b)->field_type() == MYSQL_TYPE_YEAR))
|
||||
{
|
||||
is_nulls_eq= is_owner_equal_func();
|
||||
year_as_datetime= FALSE;
|
||||
|
||||
if ((*a)->is_datetime())
|
||||
{
|
||||
year_as_datetime= TRUE;
|
||||
get_value_a_func= &get_datetime_value;
|
||||
} else if ((*a)->field_type() == MYSQL_TYPE_YEAR)
|
||||
get_value_a_func= &get_year_value;
|
||||
else
|
||||
{
|
||||
/*
|
||||
Because convert_constant_item is called only for EXECUTE in PS mode
|
||||
the value of get_value_x_func set in PREPARE might be not
|
||||
valid for EXECUTE.
|
||||
*/
|
||||
get_value_a_func= NULL;
|
||||
}
|
||||
|
||||
if ((*b)->is_datetime())
|
||||
{
|
||||
year_as_datetime= TRUE;
|
||||
get_value_b_func= &get_datetime_value;
|
||||
} else if ((*b)->field_type() == MYSQL_TYPE_YEAR)
|
||||
get_value_b_func= &get_year_value;
|
||||
else
|
||||
get_value_b_func= NULL;
|
||||
|
||||
func= &Arg_comparator::compare_year;
|
||||
return 0;
|
||||
}
|
||||
|
||||
a= cache_converted_constant(thd, a, &a_cache, type);
|
||||
@@ -983,11 +1032,11 @@ Item** Arg_comparator::cache_converted_constant(THD *thd, Item **value,
|
||||
}
|
||||
|
||||
|
||||
void Arg_comparator::set_datetime_cmp_func(Item **a1, Item **b1)
|
||||
void Arg_comparator::set_datetime_cmp_func(Item_result_field *owner_arg,
|
||||
Item **a1, Item **b1)
|
||||
{
|
||||
thd= current_thd;
|
||||
/* A caller will handle null values by itself. */
|
||||
owner= NULL;
|
||||
owner= owner_arg;
|
||||
a= a1;
|
||||
b= b1;
|
||||
a_type= (*a)->field_type();
|
||||
@@ -996,7 +1045,8 @@ void Arg_comparator::set_datetime_cmp_func(Item **a1, Item **b1)
|
||||
b_cache= 0;
|
||||
is_nulls_eq= FALSE;
|
||||
func= &Arg_comparator::compare_datetime;
|
||||
get_value_func= &get_datetime_value;
|
||||
get_value_a_func= &get_datetime_value;
|
||||
get_value_b_func= &get_datetime_value;
|
||||
}
|
||||
|
||||
|
||||
@@ -1096,6 +1146,51 @@ get_datetime_value(THD *thd, Item ***item_arg, Item **cache_arg,
|
||||
return value;
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
Retrieves YEAR value of 19XX form from given item.
|
||||
|
||||
SYNOPSIS
|
||||
get_year_value()
|
||||
thd thread handle
|
||||
item_arg [in/out] item to retrieve YEAR value from
|
||||
cache_arg [in/out] pointer to place to store the caching item to
|
||||
warn_item [in] item for issuing the conversion warning
|
||||
is_null [out] TRUE <=> the item_arg is null
|
||||
|
||||
DESCRIPTION
|
||||
Retrieves the YEAR value of 19XX form from given item for comparison by the
|
||||
compare_year() function.
|
||||
|
||||
RETURN
|
||||
obtained value
|
||||
*/
|
||||
|
||||
static longlong
|
||||
get_year_value(THD *thd, Item ***item_arg, Item **cache_arg,
|
||||
Item *warn_item, bool *is_null)
|
||||
{
|
||||
longlong value= 0;
|
||||
Item *item= **item_arg;
|
||||
|
||||
value= item->val_int();
|
||||
*is_null= item->null_value;
|
||||
if (*is_null)
|
||||
return ~(ulonglong) 0;
|
||||
|
||||
/*
|
||||
Coerce value to the 19XX form in order to correctly compare
|
||||
YEAR(2) & YEAR(4) types.
|
||||
*/
|
||||
if (value < 70)
|
||||
value+= 100;
|
||||
if (value <= 1900)
|
||||
value+= 1900;
|
||||
|
||||
return value;
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
Compare items values as dates.
|
||||
|
||||
@@ -1128,25 +1223,25 @@ int Arg_comparator::compare_datetime()
|
||||
longlong a_value, b_value;
|
||||
|
||||
/* Get DATE/DATETIME/TIME value of the 'a' item. */
|
||||
a_value= (*get_value_func)(thd, &a, &a_cache, *b, &a_is_null);
|
||||
a_value= (*get_value_a_func)(thd, &a, &a_cache, *b, &a_is_null);
|
||||
if (!is_nulls_eq && a_is_null)
|
||||
{
|
||||
if (owner)
|
||||
if (set_null)
|
||||
owner->null_value= 1;
|
||||
return -1;
|
||||
}
|
||||
|
||||
/* Get DATE/DATETIME/TIME value of the 'b' item. */
|
||||
b_value= (*get_value_func)(thd, &b, &b_cache, *a, &b_is_null);
|
||||
b_value= (*get_value_b_func)(thd, &b, &b_cache, *a, &b_is_null);
|
||||
if (a_is_null || b_is_null)
|
||||
{
|
||||
if (owner)
|
||||
if (set_null)
|
||||
owner->null_value= is_nulls_eq ? 0 : 1;
|
||||
return is_nulls_eq ? (a_is_null == b_is_null) : -1;
|
||||
}
|
||||
|
||||
/* Here we have two not-NULL values. */
|
||||
if (owner)
|
||||
if (set_null)
|
||||
owner->null_value= 0;
|
||||
|
||||
/* Compare values. */
|
||||
@@ -1159,15 +1254,17 @@ int Arg_comparator::compare_datetime()
|
||||
int Arg_comparator::compare_string()
|
||||
{
|
||||
String *res1,*res2;
|
||||
if ((res1= (*a)->val_str(&owner->tmp_value1)))
|
||||
if ((res1= (*a)->val_str(&value1)))
|
||||
{
|
||||
if ((res2= (*b)->val_str(&owner->tmp_value2)))
|
||||
if ((res2= (*b)->val_str(&value2)))
|
||||
{
|
||||
owner->null_value= 0;
|
||||
if (set_null)
|
||||
owner->null_value= 0;
|
||||
return sortcmp(res1,res2,cmp_collation.collation);
|
||||
}
|
||||
}
|
||||
owner->null_value= 1;
|
||||
if (set_null)
|
||||
owner->null_value= 1;
|
||||
return -1;
|
||||
}
|
||||
|
||||
@@ -1186,18 +1283,20 @@ int Arg_comparator::compare_string()
|
||||
int Arg_comparator::compare_binary_string()
|
||||
{
|
||||
String *res1,*res2;
|
||||
if ((res1= (*a)->val_str(&owner->tmp_value1)))
|
||||
if ((res1= (*a)->val_str(&value1)))
|
||||
{
|
||||
if ((res2= (*b)->val_str(&owner->tmp_value2)))
|
||||
if ((res2= (*b)->val_str(&value2)))
|
||||
{
|
||||
owner->null_value= 0;
|
||||
if (set_null)
|
||||
owner->null_value= 0;
|
||||
uint res1_length= res1->length();
|
||||
uint res2_length= res2->length();
|
||||
int cmp= memcmp(res1->ptr(), res2->ptr(), min(res1_length,res2_length));
|
||||
return cmp ? cmp : (int) (res1_length - res2_length);
|
||||
}
|
||||
}
|
||||
owner->null_value= 1;
|
||||
if (set_null)
|
||||
owner->null_value= 1;
|
||||
return -1;
|
||||
}
|
||||
|
||||
@@ -1210,8 +1309,8 @@ int Arg_comparator::compare_binary_string()
|
||||
int Arg_comparator::compare_e_string()
|
||||
{
|
||||
String *res1,*res2;
|
||||
res1= (*a)->val_str(&owner->tmp_value1);
|
||||
res2= (*b)->val_str(&owner->tmp_value2);
|
||||
res1= (*a)->val_str(&value1);
|
||||
res2= (*b)->val_str(&value2);
|
||||
if (!res1 || !res2)
|
||||
return test(res1 == res2);
|
||||
return test(sortcmp(res1, res2, cmp_collation.collation) == 0);
|
||||
@@ -1221,8 +1320,8 @@ int Arg_comparator::compare_e_string()
|
||||
int Arg_comparator::compare_e_binary_string()
|
||||
{
|
||||
String *res1,*res2;
|
||||
res1= (*a)->val_str(&owner->tmp_value1);
|
||||
res2= (*b)->val_str(&owner->tmp_value2);
|
||||
res1= (*a)->val_str(&value1);
|
||||
res2= (*b)->val_str(&value2);
|
||||
if (!res1 || !res2)
|
||||
return test(res1 == res2);
|
||||
return test(stringcmp(res1, res2) == 0);
|
||||
@@ -1243,13 +1342,15 @@ int Arg_comparator::compare_real()
|
||||
val2= (*b)->val_real();
|
||||
if (!(*b)->null_value)
|
||||
{
|
||||
owner->null_value= 0;
|
||||
if (set_null)
|
||||
owner->null_value= 0;
|
||||
if (val1 < val2) return -1;
|
||||
if (val1 == val2) return 0;
|
||||
return 1;
|
||||
}
|
||||
}
|
||||
owner->null_value= 1;
|
||||
if (set_null)
|
||||
owner->null_value= 1;
|
||||
return -1;
|
||||
}
|
||||
|
||||
@@ -1263,11 +1364,13 @@ int Arg_comparator::compare_decimal()
|
||||
my_decimal *val2= (*b)->val_decimal(&value2);
|
||||
if (!(*b)->null_value)
|
||||
{
|
||||
owner->null_value= 0;
|
||||
if (set_null)
|
||||
owner->null_value= 0;
|
||||
return my_decimal_cmp(val1, val2);
|
||||
}
|
||||
}
|
||||
owner->null_value= 1;
|
||||
if (set_null)
|
||||
owner->null_value= 1;
|
||||
return -1;
|
||||
}
|
||||
|
||||
@@ -1305,7 +1408,8 @@ int Arg_comparator::compare_real_fixed()
|
||||
val2= (*b)->val_real();
|
||||
if (!(*b)->null_value)
|
||||
{
|
||||
owner->null_value= 0;
|
||||
if (set_null)
|
||||
owner->null_value= 0;
|
||||
if (val1 == val2 || fabs(val1 - val2) < precision)
|
||||
return 0;
|
||||
if (val1 < val2)
|
||||
@@ -1313,7 +1417,8 @@ int Arg_comparator::compare_real_fixed()
|
||||
return 1;
|
||||
}
|
||||
}
|
||||
owner->null_value= 1;
|
||||
if (set_null)
|
||||
owner->null_value= 1;
|
||||
return -1;
|
||||
}
|
||||
|
||||
@@ -1336,13 +1441,15 @@ int Arg_comparator::compare_int_signed()
|
||||
longlong val2= (*b)->val_int();
|
||||
if (!(*b)->null_value)
|
||||
{
|
||||
owner->null_value= 0;
|
||||
if (set_null)
|
||||
owner->null_value= 0;
|
||||
if (val1 < val2) return -1;
|
||||
if (val1 == val2) return 0;
|
||||
return 1;
|
||||
}
|
||||
}
|
||||
owner->null_value= 1;
|
||||
if (set_null)
|
||||
owner->null_value= 1;
|
||||
return -1;
|
||||
}
|
||||
|
||||
@@ -1359,13 +1466,15 @@ int Arg_comparator::compare_int_unsigned()
|
||||
ulonglong val2= (*b)->val_int();
|
||||
if (!(*b)->null_value)
|
||||
{
|
||||
owner->null_value= 0;
|
||||
if (set_null)
|
||||
owner->null_value= 0;
|
||||
if (val1 < val2) return -1;
|
||||
if (val1 == val2) return 0;
|
||||
return 1;
|
||||
}
|
||||
}
|
||||
owner->null_value= 1;
|
||||
if (set_null)
|
||||
owner->null_value= 1;
|
||||
return -1;
|
||||
}
|
||||
|
||||
@@ -1382,7 +1491,8 @@ int Arg_comparator::compare_int_signed_unsigned()
|
||||
ulonglong uval2= (ulonglong)(*b)->val_int();
|
||||
if (!(*b)->null_value)
|
||||
{
|
||||
owner->null_value= 0;
|
||||
if (set_null)
|
||||
owner->null_value= 0;
|
||||
if (sval1 < 0 || (ulonglong)sval1 < uval2)
|
||||
return -1;
|
||||
if ((ulonglong)sval1 == uval2)
|
||||
@@ -1390,7 +1500,8 @@ int Arg_comparator::compare_int_signed_unsigned()
|
||||
return 1;
|
||||
}
|
||||
}
|
||||
owner->null_value= 1;
|
||||
if (set_null)
|
||||
owner->null_value= 1;
|
||||
return -1;
|
||||
}
|
||||
|
||||
@@ -1407,7 +1518,8 @@ int Arg_comparator::compare_int_unsigned_signed()
|
||||
longlong sval2= (*b)->val_int();
|
||||
if (!(*b)->null_value)
|
||||
{
|
||||
owner->null_value= 0;
|
||||
if (set_null)
|
||||
owner->null_value= 0;
|
||||
if (sval2 < 0)
|
||||
return 1;
|
||||
if (uval1 < (ulonglong)sval2)
|
||||
@@ -1417,7 +1529,8 @@ int Arg_comparator::compare_int_unsigned_signed()
|
||||
return 1;
|
||||
}
|
||||
}
|
||||
owner->null_value= 1;
|
||||
if (set_null)
|
||||
owner->null_value= 1;
|
||||
return -1;
|
||||
}
|
||||
|
||||
@@ -1453,10 +1566,11 @@ int Arg_comparator::compare_row()
|
||||
for (uint i= 0; i<n; i++)
|
||||
{
|
||||
res= comparators[i].compare();
|
||||
if (owner->null_value)
|
||||
/* Aggregate functions don't need special null handling. */
|
||||
if (owner->null_value && owner->type() == Item::FUNC_ITEM)
|
||||
{
|
||||
// NULL was compared
|
||||
switch (owner->functype()) {
|
||||
switch (((Item_func*)owner)->functype()) {
|
||||
case Item_func::NE_FUNC:
|
||||
break; // NE never aborts on NULL even if abort_on_null is set
|
||||
case Item_func::LT_FUNC:
|
||||
@@ -1465,7 +1579,7 @@ int Arg_comparator::compare_row()
|
||||
case Item_func::GE_FUNC:
|
||||
return -1; // <, <=, > and >= always fail on NULL
|
||||
default: // EQ_FUNC
|
||||
if (owner->abort_on_null)
|
||||
if (((Item_bool_func2*)owner)->abort_on_null)
|
||||
return -1; // We do not need correct NULL returning
|
||||
}
|
||||
was_null= 1;
|
||||
@@ -1502,6 +1616,67 @@ int Arg_comparator::compare_e_row()
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
Compare values as YEAR.
|
||||
|
||||
@details
|
||||
Compare items as YEAR for EQUAL_FUNC and for other comparison functions.
|
||||
The YEAR values of form 19XX are obtained with help of the get_year_value()
|
||||
function.
|
||||
If one of arguments is of DATE/DATETIME type its value is obtained
|
||||
with help of the get_datetime_value function. In this case YEAR values
|
||||
prior to comparison are converted to the ulonglong YYYY-00-00 00:00:00
|
||||
DATETIME form.
|
||||
If an argument type neither YEAR nor DATE/DATEIME then val_int function
|
||||
is used to obtain value for comparison.
|
||||
|
||||
RETURN
|
||||
If is_nulls_eq is TRUE:
|
||||
1 if items are equal or both are null
|
||||
0 otherwise
|
||||
If is_nulls_eq is FALSE:
|
||||
-1 a < b
|
||||
0 a == b or at least one of items is null
|
||||
1 a > b
|
||||
See the table:
|
||||
is_nulls_eq | 1 | 1 | 1 | 1 | 0 | 0 | 0 | 0 |
|
||||
a_is_null | 1 | 0 | 1 | 0 | 1 | 0 | 1 | 0 |
|
||||
b_is_null | 1 | 1 | 0 | 0 | 1 | 1 | 0 | 0 |
|
||||
result | 1 | 0 | 0 |0/1| 0 | 0 | 0 |-1/0/1|
|
||||
*/
|
||||
|
||||
int Arg_comparator::compare_year()
|
||||
{
|
||||
bool a_is_null, b_is_null;
|
||||
ulonglong val1= get_value_a_func ?
|
||||
(*get_value_a_func)(thd, &a, &a_cache, *b, &a_is_null) :
|
||||
(*a)->val_int();
|
||||
ulonglong val2= get_value_b_func ?
|
||||
(*get_value_b_func)(thd, &b, &b_cache, *a, &b_is_null) :
|
||||
(*b)->val_int();
|
||||
if (!(*a)->null_value)
|
||||
{
|
||||
if (!(*b)->null_value)
|
||||
{
|
||||
if (set_null)
|
||||
owner->null_value= 0;
|
||||
/* Convert year to DATETIME of form YYYY-00-00 00:00:00 when necessary. */
|
||||
if((*a)->field_type() == MYSQL_TYPE_YEAR && year_as_datetime)
|
||||
val1*= 10000000000LL;
|
||||
if((*b)->field_type() == MYSQL_TYPE_YEAR && year_as_datetime)
|
||||
val2*= 10000000000LL;
|
||||
|
||||
if (val1 < val2) return is_nulls_eq ? 0 : -1;
|
||||
if (val1 == val2) return is_nulls_eq ? 1 : 0;
|
||||
return is_nulls_eq ? 0 : 1;
|
||||
}
|
||||
}
|
||||
if (set_null)
|
||||
owner->null_value= is_nulls_eq ? 0 : 1;
|
||||
return (is_nulls_eq && (*a)->null_value == (*b)->null_value) ? 1 : 0;
|
||||
}
|
||||
|
||||
|
||||
void Item_func_truth::fix_length_and_dec()
|
||||
{
|
||||
maybe_null= 0;
|
||||
@@ -1789,8 +1964,8 @@ longlong Item_func_lt::val_int()
|
||||
longlong Item_func_strcmp::val_int()
|
||||
{
|
||||
DBUG_ASSERT(fixed == 1);
|
||||
String *a=args[0]->val_str(&tmp_value1);
|
||||
String *b=args[1]->val_str(&tmp_value2);
|
||||
String *a=args[0]->val_str(&cmp.value1);
|
||||
String *b=args[1]->val_str(&cmp.value2);
|
||||
if (!a || !b)
|
||||
{
|
||||
null_value=1;
|
||||
@@ -2073,8 +2248,8 @@ void Item_func_between::fix_length_and_dec()
|
||||
|
||||
if (compare_as_dates)
|
||||
{
|
||||
ge_cmp.set_datetime_cmp_func(args, args + 1);
|
||||
le_cmp.set_datetime_cmp_func(args, args + 2);
|
||||
ge_cmp.set_datetime_cmp_func(this, args, args + 1);
|
||||
le_cmp.set_datetime_cmp_func(this, args, args + 2);
|
||||
}
|
||||
else if (time_items_found == 3)
|
||||
{
|
||||
@@ -4402,13 +4577,13 @@ void Item_func_isnotnull::print(String *str, enum_query_type query_type)
|
||||
longlong Item_func_like::val_int()
|
||||
{
|
||||
DBUG_ASSERT(fixed == 1);
|
||||
String* res = args[0]->val_str(&tmp_value1);
|
||||
String* res = args[0]->val_str(&cmp.value1);
|
||||
if (args[0]->null_value)
|
||||
{
|
||||
null_value=1;
|
||||
return 0;
|
||||
}
|
||||
String* res2 = args[1]->val_str(&tmp_value2);
|
||||
String* res2 = args[1]->val_str(&cmp.value2);
|
||||
if (args[1]->null_value)
|
||||
{
|
||||
null_value=1;
|
||||
@@ -4432,7 +4607,7 @@ Item_func::optimize_type Item_func_like::select_optimize() const
|
||||
{
|
||||
if (args[1]->const_item())
|
||||
{
|
||||
String* res2= args[1]->val_str((String *)&tmp_value2);
|
||||
String* res2= args[1]->val_str((String *)&cmp.value2);
|
||||
|
||||
if (!res2)
|
||||
return OPTIMIZE_NONE;
|
||||
@@ -4463,7 +4638,7 @@ bool Item_func_like::fix_fields(THD *thd, Item **ref)
|
||||
if (escape_item->const_item())
|
||||
{
|
||||
/* If we are on execution stage */
|
||||
String *escape_str= escape_item->val_str(&tmp_value1);
|
||||
String *escape_str= escape_item->val_str(&cmp.value1);
|
||||
if (escape_str)
|
||||
{
|
||||
if (escape_used_in_parsing && (
|
||||
@@ -4518,7 +4693,7 @@ bool Item_func_like::fix_fields(THD *thd, Item **ref)
|
||||
if (args[1]->const_item() && !use_strnxfrm(collation.collation) &&
|
||||
!(specialflag & SPECIAL_NO_NEW_FUNC))
|
||||
{
|
||||
String* res2 = args[1]->val_str(&tmp_value2);
|
||||
String* res2 = args[1]->val_str(&cmp.value2);
|
||||
if (!res2)
|
||||
return FALSE; // Null argument
|
||||
|
||||
|
Reference in New Issue
Block a user