summaryrefslogtreecommitdiff
path: root/sql
diff options
context:
space:
mode:
authorunknown <sanja@montyprogram.com>2013-08-20 14:48:29 +0300
committerunknown <sanja@montyprogram.com>2013-08-20 14:48:29 +0300
commit35b2883643e337a8ec9c3cf7494363ae9889119c (patch)
treeeb2e7d833ed965b30f8b8485cfdac31abfea6c97 /sql
parentdafa458262fb47a2c9534bcc36088b15e26307c2 (diff)
parentb59738a598569ace75be5e63b7ed6ca69afe6ebc (diff)
downloadmariadb-git-35b2883643e337a8ec9c3cf7494363ae9889119c.tar.gz
merge 5.5 -> 10.0-base
Diffstat (limited to 'sql')
-rw-r--r--sql/item.cc3
-rw-r--r--sql/item_cmpfunc.cc56
-rw-r--r--sql/item_func.cc15
-rw-r--r--sql/item_func.h33
-rw-r--r--sql/item_timefunc.cc8
-rw-r--r--sql/sql_cache.cc12
-rw-r--r--sql/sql_select.cc6
-rw-r--r--sql/sql_union.cc2
-rw-r--r--sql/sys_vars.h3
9 files changed, 111 insertions, 27 deletions
diff --git a/sql/item.cc b/sql/item.cc
index f90469a66a7..d99f5ff46ea 100644
--- a/sql/item.cc
+++ b/sql/item.cc
@@ -297,7 +297,8 @@ String *Item::val_string_from_decimal(String *str)
String *Item::val_string_from_date(String *str)
{
MYSQL_TIME ltime;
- if (get_date(&ltime, 0) ||
+ if (get_date(&ltime,
+ field_type() == MYSQL_TYPE_TIME ? TIME_TIME_ONLY : 0) ||
str->alloc(MAX_DATE_STRING_REP_LENGTH))
{
null_value= 1;
diff --git a/sql/item_cmpfunc.cc b/sql/item_cmpfunc.cc
index 155a9afdafe..706b47618da 100644
--- a/sql/item_cmpfunc.cc
+++ b/sql/item_cmpfunc.cc
@@ -4341,12 +4341,40 @@ Item_cond::fix_fields(THD *thd, Item **ref)
return TRUE; /* purecov: inspected */
used_tables_cache|= item->used_tables();
if (item->const_item())
- and_tables_cache= (table_map) 0;
+ {
+ if (!item->is_expensive() && item->val_int() == 0)
+ {
+ /*
+ This is "... OR false_cond OR ..."
+ In this case, false_cond has no effect on cond_or->not_null_tables()
+ */
+ }
+ else
+ {
+ /*
+ This is "... OR const_cond OR ..."
+ In this case, cond_or->not_null_tables()=0, because the condition
+ some_cond_or might be true regardless of what tables are
+ NULL-complemented.
+ */
+ and_tables_cache= (table_map) 0;
+ }
+ }
else
{
- table_map tmp_table_map= item->not_null_tables();
- not_null_tables_cache|= tmp_table_map;
- and_tables_cache&= tmp_table_map;
+ /*
+ If an item is a
+ - constant
+ - inexpensive
+ - its value is 0
+ then we don't need to account it in not_null_tables_cache
+ */
+ //if (!(item->const_item() && !item->is_expensive() ))
+ {
+ table_map tmp_table_map= item->not_null_tables();
+ not_null_tables_cache|= tmp_table_map;
+ and_tables_cache&= tmp_table_map;
+ }
const_item_cache= FALSE;
}
@@ -4374,7 +4402,25 @@ Item_cond::eval_not_null_tables(uchar *opt_arg)
{
table_map tmp_table_map;
if (item->const_item())
- and_tables_cache= (table_map) 0;
+ {
+ if (!item->is_expensive() && item->val_int() == 0)
+ {
+ /*
+ This is "... OR false_cond OR ..."
+ In this case, false_cond has no effect on cond_or->not_null_tables()
+ */
+ }
+ else
+ {
+ /*
+ This is "... OR const_cond OR ..."
+ In this case, cond_or->not_null_tables()=0, because the condition
+ some_cond_or might be true regardless of what tables are
+ NULL-complemented.
+ */
+ and_tables_cache= (table_map) 0;
+ }
+ }
else
{
tmp_table_map= item->not_null_tables();
diff --git a/sql/item_func.cc b/sql/item_func.cc
index 1bd288fc4b0..4c7b8fce98b 100644
--- a/sql/item_func.cc
+++ b/sql/item_func.cc
@@ -2791,6 +2791,13 @@ bool Item_func_min_max::get_date(MYSQL_TIME *ltime, ulonglong fuzzy_date)
ltime->time_type= MYSQL_TIMESTAMP_DATE;
ltime->hour= ltime->minute= ltime->second= ltime->second_part= 0;
}
+ else if (compare_as_dates->field_type() == MYSQL_TYPE_TIME)
+ {
+ ltime->time_type= MYSQL_TIMESTAMP_TIME;
+ ltime->hour+= (ltime->month * 32 + ltime->day) * 24;
+ ltime->month= ltime->day= 0;
+ }
+
return (null_value= 0);
}
@@ -4067,9 +4074,7 @@ longlong Item_func_get_lock::val_int()
if (!ull_name_ok(res))
DBUG_RETURN(0);
-
- DBUG_PRINT("info", ("lock %.*s, thd=%ld", res->length(), res->ptr(),
- (long) thd->real_id));
+ DBUG_PRINT("enter", ("lock: %.*s", res->length(), res->ptr()));
/* HASH entries are of type User_level_lock. */
if (! my_hash_inited(&thd->ull_hash) &&
my_hash_init(&thd->ull_hash, &my_charset_bin,
@@ -4090,6 +4095,7 @@ longlong Item_func_get_lock::val_int()
/* Recursive lock */
ull->refs++;
null_value = 0;
+ DBUG_PRINT("info", ("recursive lock, ref-count: %d", (int) ull->refs));
DBUG_RETURN(1);
}
@@ -4146,7 +4152,7 @@ longlong Item_func_release_lock::val_int()
if (!ull_name_ok(res))
DBUG_RETURN(0);
- DBUG_PRINT("info", ("lock %.*s", res->length(), res->ptr()));
+ DBUG_PRINT("enter", ("lock: %.*s", res->length(), res->ptr()));
MDL_key ull_key;
ull_key.mdl_key_init(MDL_key::USER_LOCK, res->c_ptr_safe(), "");
@@ -4160,6 +4166,7 @@ longlong Item_func_release_lock::val_int()
null_value= thd->mdl_context.get_lock_owner(&ull_key) == 0;
DBUG_RETURN(0);
}
+ DBUG_PRINT("info", ("ref count: %d", (int) ull->refs));
null_value= 0;
if (--ull->refs == 0)
{
diff --git a/sql/item_func.h b/sql/item_func.h
index bbe70724f79..499ad9f1893 100644
--- a/sql/item_func.h
+++ b/sql/item_func.h
@@ -43,7 +43,14 @@ protected:
bool persistent_maybe_null;
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,
@@ -1269,11 +1276,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)
{
@@ -1523,6 +1530,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());
@@ -1537,6 +1550,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());
@@ -1629,6 +1648,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"; }
diff --git a/sql/item_timefunc.cc b/sql/item_timefunc.cc
index e777ecf121e..c82fb3dd0f2 100644
--- a/sql/item_timefunc.cc
+++ b/sql/item_timefunc.cc
@@ -2032,7 +2032,9 @@ bool Item_date_add_interval::get_date(MYSQL_TIME *ltime, ulonglong fuzzy_date)
{
INTERVAL interval;
- if (args[0]->get_date(ltime, 0) ||
+ if (args[0]->get_date(ltime,
+ cached_field_type == MYSQL_TYPE_TIME ?
+ TIME_TIME_ONLY : 0) ||
get_interval_value(args[1], int_type, &interval))
return (null_value=1);
@@ -2423,7 +2425,9 @@ bool Item_time_typecast::get_date(MYSQL_TIME *ltime, ulonglong fuzzy_date)
if (ltime->time_type != MYSQL_TIMESTAMP_TIME)
ltime->year= ltime->month= ltime->day= 0;
ltime->time_type= MYSQL_TIMESTAMP_TIME;
- return 0;
+ return (fuzzy_date & TIME_TIME_ONLY) ? 0 :
+ (null_value= check_date_with_warn(ltime, fuzzy_date,
+ MYSQL_TIMESTAMP_ERROR));
}
diff --git a/sql/sql_cache.cc b/sql/sql_cache.cc
index 2f4efab2cb8..bcc18d316c8 100644
--- a/sql/sql_cache.cc
+++ b/sql/sql_cache.cc
@@ -1312,17 +1312,17 @@ ulong Query_cache::resize(ulong query_cache_size_arg)
{
BLOCK_LOCK_WR(block);
Query_cache_query *query= block->query();
- if (query && query->writer())
+ if (query->writer())
{
/*
- Drop the writer; this will cancel any attempts to store
+ Drop the writer; this will cancel any attempts to store
the processed statement associated with this writer.
*/
query->writer()->first_query_block= NULL;
query->writer(0);
refused++;
}
- BLOCK_UNLOCK_WR(block);
+ query->unlock_n_destroy();
block= block->next;
} while (block != queries_blocks);
}
@@ -4247,11 +4247,11 @@ my_bool Query_cache::move_by_type(uchar **border,
size_t key_length;
key=query_cache_query_get_key((uchar*) block, &key_length, 0);
my_hash_first(&queries, (uchar*) key, key_length, &record_idx);
- // Move table of used tables
- memmove((char*) new_block->table(0), (char*) block->table(0),
- ALIGN_SIZE(n_tables*sizeof(Query_cache_block_table)));
block->query()->unlock_n_destroy();
block->destroy();
+ // Move table of used tables
+ memmove((char*) new_block->table(0), (char*) block->table(0),
+ ALIGN_SIZE(n_tables*sizeof(Query_cache_block_table)));
new_block->init(len);
new_block->type=Query_cache_block::QUERY;
new_block->used=used;
diff --git a/sql/sql_select.cc b/sql/sql_select.cc
index 727dfc94175..3bb62598027 100644
--- a/sql/sql_select.cc
+++ b/sql/sql_select.cc
@@ -8957,10 +8957,6 @@ make_join_select(JOIN *join,SQL_SELECT *select,COND *cond)
{ /* there may be a select without a cond. */
if (join->table_count > 1)
cond->update_used_tables(); // Tablenr may have changed
- if (join->const_tables == join->table_count &&
- thd->lex->current_select->master_unit() ==
- &thd->lex->unit) // not upper level SELECT
- join->const_table_map|=RAND_TABLE_BIT;
/*
Extract expressions that depend on constant tables
@@ -16171,6 +16167,8 @@ create_internal_tmp_table_from_heap2(THD *thd, TABLE *table,
const char *save_proc_info;
int write_err= 0;
DBUG_ENTER("create_internal_tmp_table_from_heap2");
+ if (is_duplicate)
+ *is_duplicate= FALSE;
if (table->s->db_type() != heap_hton ||
error != HA_ERR_RECORD_FILE_FULL)
diff --git a/sql/sql_union.cc b/sql/sql_union.cc
index 82808708889..0950cd371eb 100644
--- a/sql/sql_union.cc
+++ b/sql/sql_union.cc
@@ -83,7 +83,7 @@ int select_union::send_data(List<Item> &values)
*/
return -1;
}
- bool is_duplicate;
+ bool is_duplicate= FALSE;
/* create_internal_tmp_table_from_heap will generate error if needed */
if (table->file->is_fatal_error(write_err, HA_CHECK_DUP) &&
create_internal_tmp_table_from_heap(thd, table,
diff --git a/sql/sys_vars.h b/sql/sys_vars.h
index d68761d91ca..260a8af8384 100644
--- a/sql/sys_vars.h
+++ b/sql/sys_vars.h
@@ -428,7 +428,10 @@ public:
void cleanup()
{
if (flags & ALLOCATED)
+ {
my_free(global_var(char*));
+ global_var(char *)= NULL;
+ }
flags&= ~ALLOCATED;
}
static bool do_string_check(THD *thd, set_var *var, CHARSET_INFO *charset)