#At file:///export/home/didrik/repo/trunk-merge/ based on revid:bjorn.munch@stripped
3120 Tor Didriksen 2011-05-26 [merge]
Automerge opt-team => trunk
modified:
sql/item_subselect.cc
sql/sql_array.h
sql/sql_base.cc
sql/sql_select.cc
sql/sql_select.h
=== modified file 'sql/item_subselect.cc'
--- a/sql/item_subselect.cc 2011-04-06 11:13:33 +0000
+++ b/sql/item_subselect.cc 2011-05-24 09:36:11 +0000
@@ -3181,23 +3181,24 @@ bool subselect_hash_sj_engine::setup(Lis
- here we initialize only those members that are used by
subselect_uniquesubquery_engine, so these objects are incomplete.
*/
- if (!(tab= new (thd->mem_root) JOIN_TAB))
+ JOIN_TAB * const tmp_tab= new (thd->mem_root) JOIN_TAB;
+ if (tmp_tab == NULL)
DBUG_RETURN(TRUE);
- tab->table= tmp_table;
- tab->ref.key= 0; /* The only temp table index. */
- tab->ref.key_length= tmp_key->key_length;
- if (!(tab->ref.key_buff=
+ tmp_tab->table= tmp_table;
+ tmp_tab->ref.key= 0; /* The only temp table index. */
+ tmp_tab->ref.key_length= tmp_key->key_length;
+ if (!(tmp_tab->ref.key_buff=
(uchar*) thd->calloc(ALIGN_SIZE(tmp_key->key_length) * 2)) ||
- !(tab->ref.key_copy=
+ !(tmp_tab->ref.key_copy=
(store_key**) thd->alloc((sizeof(store_key*) *
(tmp_key_parts + 1)))) ||
- !(tab->ref.items=
+ !(tmp_tab->ref.items=
(Item**) thd->alloc(sizeof(Item*) * tmp_key_parts)))
DBUG_RETURN(TRUE);
KEY_PART_INFO *cur_key_part= tmp_key->key_part;
- store_key **ref_key= tab->ref.key_copy;
- uchar *cur_ref_buff= tab->ref.key_buff;
+ store_key **ref_key= tmp_tab->ref.key_copy;
+ uchar *cur_ref_buff= tmp_tab->ref.key_buff;
/*
Create an artificial condition to post-filter those rows matched by index
@@ -3235,10 +3236,10 @@ bool subselect_hash_sj_engine::setup(Lis
/* Item for the corresponding field from the materialized temp table. */
Item_field *right_col_item;
int null_count= test(cur_key_part->field->real_maybe_null());
- tab->ref.items[i]= item_in->left_expr->element_index(i);
+ tmp_tab->ref.items[i]= item_in->left_expr->element_index(i);
if (!(right_col_item= new Item_field(thd, context, cur_key_part->field)) ||
- !(eq_cond= new Item_func_eq(tab->ref.items[i], right_col_item)) ||
+ !(eq_cond= new Item_func_eq(tmp_tab->ref.items[i], right_col_item)) ||
((Item_cond_and*)cond)->add(eq_cond))
{
delete cond;
@@ -3255,16 +3256,19 @@ bool subselect_hash_sj_engine::setup(Lis
*/
cur_ref_buff + null_count,
null_count ? cur_ref_buff : 0,
- cur_key_part->length, tab->ref.items[i]);
+ cur_key_part->length, tmp_tab->ref.items[i]);
cur_ref_buff+= cur_key_part->store_length;
}
*ref_key= NULL; /* End marker. */
- tab->ref.key_err= 1;
- tab->ref.key_parts= tmp_key_parts;
+ tmp_tab->ref.key_err= 1;
+ tmp_tab->ref.key_parts= tmp_key_parts;
if (cond->fix_fields(thd, &cond))
DBUG_RETURN(TRUE);
+ // Set 'tab' only when function cannot fail, because of assert in destructor
+ tab= tmp_tab;
+
/*
Create and optimize the JOIN that will be used to materialize
the subquery if not yet created.
=== modified file 'sql/sql_array.h'
--- a/sql/sql_array.h 2010-11-05 22:14:29 +0000
+++ b/sql/sql_array.h 2011-05-18 13:12:02 +0000
@@ -79,75 +79,4 @@ public:
}
};
-
-/*
- Array of pointers to Elem that uses memory from MEM_ROOT
-
- MEM_ROOT has no realloc() so this is supposed to be used for cases when
- reallocations are rare.
-*/
-
-template <class Elem> class Array
-{
- enum {alloc_increment = 16};
- Elem **buffer;
- uint n_elements, max_element;
-public:
- Array(MEM_ROOT *mem_root, uint prealloc=16)
- {
- buffer= (Elem**)alloc_root(mem_root, prealloc * sizeof(Elem**));
- max_element = buffer? prealloc : 0;
- n_elements= 0;
- }
-
- Elem& at(int idx)
- {
- return *(((Elem*)buffer) + idx);
- }
-
- Elem **front()
- {
- return buffer;
- }
-
- Elem **back()
- {
- return buffer + n_elements;
- }
-
- bool append(MEM_ROOT *mem_root, Elem *el)
- {
- if (n_elements == max_element)
- {
- Elem **newbuf;
- if (!(newbuf= (Elem**)alloc_root(mem_root, (n_elements + alloc_increment)*
- sizeof(Elem**))))
- {
- return FALSE;
- }
- memcpy(newbuf, buffer, n_elements*sizeof(Elem*));
- buffer= newbuf;
- }
- buffer[n_elements++]= el;
- return FALSE;
- }
-
- int elements()
- {
- return n_elements;
- }
-
- void clear()
- {
- n_elements= 0;
- }
-
- typedef int (*CMP_FUNC)(Elem * const *el1, Elem *const *el2);
-
- void sort(CMP_FUNC cmp_func)
- {
- my_qsort(buffer, n_elements, sizeof(Elem*), (qsort_cmp)cmp_func);
- }
-};
-
#endif /* SQL_ARRAY_INCLUDED */
=== modified file 'sql/sql_base.cc'
--- a/sql/sql_base.cc 2011-05-21 08:25:33 +0000
+++ b/sql/sql_base.cc 2011-05-26 08:39:40 +0000
@@ -6876,9 +6876,29 @@ find_field_in_tables(THD *thd, Item_iden
if (last_table)
last_table= last_table->next_name_resolution_table;
+#ifndef DBUG_OFF
+ uint loop_count= 0;
+ TABLE_LIST *one_node;
+#endif
for (; cur_table != last_table ;
cur_table= cur_table->next_name_resolution_table)
{
+#ifndef DBUG_OFF
+ ++loop_count;
+ if (loop_count == 1000) // not normal, record one node we meet
+ one_node= cur_table;
+ if ((loop_count > 1000) && (one_node == cur_table))
+ {
+ /*
+ Meeting same node again: cycle, infinite loop. Raise an error which
+ doesn't stop RQG, so that Roel can continue working while we fix the
+ bug. We cannot continue the statement though.
+ */
+ my_error(ER_WRONG_FIELD_WITH_GROUP, MYF(0),
+ "HITTING BUG#12567331 INFINITE LOOP DETECTED - ASK GUILHEM AND ROEL");
+ return NULL;
+ }
+#endif
Field *cur_field= find_field_in_table_ref(thd, cur_table, name, length,
item->name, db, table_name, ref,
(thd->lex->sql_command ==
=== modified file 'sql/sql_select.cc'
--- a/sql/sql_select.cc 2011-05-18 10:43:46 +0000
+++ b/sql/sql_select.cc 2011-05-26 06:03:02 +0000
@@ -978,7 +978,7 @@ bool resolve_subquery(THD *thd, JOIN *jo
/* Register the subquery for further processing in flatten_subqueries() */
select_lex->outer_select()->join->
- sj_subselects.append(thd->mem_root, in_exists_predicate);
+ sj_subselects.push_back(in_exists_predicate);
}
else
{
@@ -4170,11 +4170,11 @@ bool JOIN::flatten_subqueries()
Item_exists_subselect **subq_end;
DBUG_ENTER("JOIN::flatten_subqueries");
- if (sj_subselects.elements() == 0)
+ if (sj_subselects.empty())
DBUG_RETURN(FALSE);
/* First, convert child join's subqueries. We proceed bottom-up here */
- for (subq= sj_subselects.front(), subq_end= sj_subselects.back();
+ for (subq= sj_subselects.begin(), subq_end= sj_subselects.end();
subq != subq_end;
subq++)
{
@@ -4207,7 +4207,7 @@ bool JOIN::flatten_subqueries()
{
if (tbl->on_expr || tbl->in_outer_join_nest())
{
- subq= sj_subselects.front();
+ subq= sj_subselects.begin();
arena= thd->activate_stmt_arena_if_needed(&backup);
goto skip_conversion;
}
@@ -4220,11 +4220,14 @@ bool JOIN::flatten_subqueries()
- prefer correlated subqueries over uncorrelated;
- prefer subqueries that have greater number of outer tables;
*/
- sj_subselects.sort(subq_sj_candidate_cmp);
+ my_qsort(sj_subselects.begin(),
+ sj_subselects.size(), sj_subselects.element_size(),
+ reinterpret_cast<qsort_cmp>(subq_sj_candidate_cmp));
+
// #tables-in-parent-query + #tables-in-subquery < MAX_TABLES
/* Replace all subqueries to be flattened with Item_int(1) */
arena= thd->activate_stmt_arena_if_needed(&backup);
- for (subq= sj_subselects.front();
+ for (subq= sj_subselects.begin();
subq != subq_end &&
tables + (*subq)->unit->first_select()->join->tables < MAX_TABLES;
subq++)
@@ -4235,7 +4238,7 @@ bool JOIN::flatten_subqueries()
DBUG_RETURN(TRUE); /* purecov: inspected */
}
- for (subq= sj_subselects.front();
+ for (subq= sj_subselects.begin();
subq != subq_end &&
tables + (*subq)->unit->first_select()->join->tables < MAX_TABLES;
subq++)
=== modified file 'sql/sql_select.h'
--- a/sql/sql_select.h 2011-05-18 10:43:46 +0000
+++ b/sql/sql_select.h 2011-05-26 06:03:02 +0000
@@ -1888,7 +1888,8 @@ public:
bool union_part; ///< this subselect is part of union
bool optimized; ///< flag to avoid double optimization in EXPLAIN
- Array<Item_exists_subselect> sj_subselects;
+ // true: No need to run DTORs on pointers.
+ Mem_root_array<Item_exists_subselect*, true> sj_subselects;
/* Temporary tables used to weed-out semi-join duplicates */
List<TABLE> sj_tmp_tables;
@@ -1913,7 +1914,7 @@ public:
select_result *result_arg)
: keyuse(thd_arg->mem_root),
fields_list(fields_arg),
- sj_subselects(thd_arg->mem_root, 4)
+ sj_subselects(thd_arg->mem_root)
{
init(thd_arg, fields_arg, select_options_arg, result_arg);
}
No bundle (reason: revision is a merge (you can force generation of a bundle with env var BZR_FORCE_BUNDLE=1)).
| Thread |
|---|
| • bzr commit into mysql-trunk branch (tor.didriksen:3120) | Tor Didriksen | 26 May |