Commit 61a771df authored by Alexander Barkov's avatar Alexander Barkov

Moving a part of st_select_lex_unit::prepare() into a new method prepare_join()

This is to simplify the logic inside st_select_lex_unit::prepare(),
to implement data type aggregation for pluggable data types.
parent 2fd63540
...@@ -749,6 +749,9 @@ class st_select_lex_unit: public st_select_lex_node { ...@@ -749,6 +749,9 @@ class st_select_lex_unit: public st_select_lex_node {
/* UNION methods */ /* UNION methods */
bool prepare(THD *thd, select_result *result, ulong additional_options); bool prepare(THD *thd, select_result *result, ulong additional_options);
bool prepare_join(THD *thd, SELECT_LEX *sl, select_result *result,
ulong additional_options,
bool is_union_select);
bool optimize(); bool optimize();
bool exec(); bool exec();
bool exec_recursive(); bool exec_recursive();
......
...@@ -636,6 +636,59 @@ st_select_lex_unit::init_prepare_fake_select_lex(THD *thd_arg, ...@@ -636,6 +636,59 @@ st_select_lex_unit::init_prepare_fake_select_lex(THD *thd_arg,
} }
bool st_select_lex_unit::prepare_join(THD *thd_arg, SELECT_LEX *sl,
select_result *tmp_result,
ulong additional_options,
bool is_union_select)
{
DBUG_ENTER("st_select_lex_unit::prepare_join");
bool can_skip_order_by;
sl->options|= SELECT_NO_UNLOCK;
JOIN *join= new JOIN(thd_arg, sl->item_list,
(sl->options | thd_arg->variables.option_bits |
additional_options),
tmp_result);
if (!join)
DBUG_RETURN(true);
thd_arg->lex->current_select= sl;
can_skip_order_by= is_union_select && !(sl->braces && sl->explicit_limit);
saved_error= join->prepare(sl->table_list.first,
sl->with_wild,
sl->where,
(can_skip_order_by ? 0 :
sl->order_list.elements) +
sl->group_list.elements,
can_skip_order_by ?
NULL : sl->order_list.first,
can_skip_order_by,
sl->group_list.first,
sl->having,
(is_union_select ? NULL :
thd_arg->lex->proc_list.first),
sl, this);
/* There are no * in the statement anymore (for PS) */
sl->with_wild= 0;
last_procedure= join->procedure;
if (saved_error || (saved_error= thd_arg->is_fatal_error))
DBUG_RETURN(true);
/*
Remove all references from the select_lex_units to the subqueries that
are inside the ORDER BY clause.
*/
if (can_skip_order_by)
{
for (ORDER *ord= (ORDER *)sl->order_list.first; ord; ord= ord->next)
{
(*ord->item)->walk(&Item::eliminate_subselect_processor, FALSE, NULL);
}
}
DBUG_RETURN(false);
}
bool st_select_lex_unit::prepare(THD *thd_arg, select_result *sel_result, bool st_select_lex_unit::prepare(THD *thd_arg, select_result *sel_result,
...@@ -747,15 +800,22 @@ bool st_select_lex_unit::prepare(THD *thd_arg, select_result *sel_result, ...@@ -747,15 +800,22 @@ bool st_select_lex_unit::prepare(THD *thd_arg, select_result *sel_result,
tmp_result= sel_result; tmp_result= sel_result;
sl->context.resolve_in_select_list= TRUE; sl->context.resolve_in_select_list= TRUE;
if (!is_union_select && !is_recursive)
{
if (prepare_join(thd_arg, first_sl, tmp_result, additional_options,
is_union_select))
goto err;
types= first_sl->item_list;
goto cont;
}
for (;sl; sl= sl->next_select()) for (;sl; sl= sl->next_select())
{ {
bool can_skip_order_by; if (prepare_join(thd_arg, sl, tmp_result, additional_options,
sl->options|= SELECT_NO_UNLOCK; is_union_select))
JOIN *join= new JOIN(thd_arg, sl->item_list, goto err;
(sl->options | thd_arg->variables.option_bits |
additional_options),
tmp_result);
/* /*
setup_tables_done_option should be set only for very first SELECT, setup_tables_done_option should be set only for very first SELECT,
because it protect from secont setup_tables call for select-like non because it protect from secont setup_tables call for select-like non
...@@ -763,53 +823,12 @@ bool st_select_lex_unit::prepare(THD *thd_arg, select_result *sel_result, ...@@ -763,53 +823,12 @@ bool st_select_lex_unit::prepare(THD *thd_arg, select_result *sel_result,
SELECT (for union it can be only INSERT ... SELECT). SELECT (for union it can be only INSERT ... SELECT).
*/ */
additional_options&= ~OPTION_SETUP_TABLES_DONE; additional_options&= ~OPTION_SETUP_TABLES_DONE;
if (!join)
goto err;
thd_arg->lex->current_select= sl;
can_skip_order_by= is_union_select && !(sl->braces && sl->explicit_limit);
saved_error= join->prepare(sl->table_list.first,
sl->with_wild,
sl->where,
(can_skip_order_by ? 0 :
sl->order_list.elements) +
sl->group_list.elements,
can_skip_order_by ?
NULL : sl->order_list.first,
can_skip_order_by,
sl->group_list.first,
sl->having,
(is_union_select ? NULL :
thd_arg->lex->proc_list.first),
sl, this);
/* There are no * in the statement anymore (for PS) */
sl->with_wild= 0;
last_procedure= join->procedure;
if (saved_error || (saved_error= thd_arg->is_fatal_error))
goto err;
/*
Remove all references from the select_lex_units to the subqueries that
are inside the ORDER BY clause.
*/
if (can_skip_order_by)
{
for (ORDER *ord= (ORDER *)sl->order_list.first; ord; ord= ord->next)
{
(*ord->item)->walk(&Item::eliminate_subselect_processor, FALSE, NULL);
}
}
/* /*
Use items list of underlaid select for derived tables to preserve Use items list of underlaid select for derived tables to preserve
information about fields lengths and exact types information about fields lengths and exact types
*/ */
if (!is_union_select && !is_recursive) if (sl == first_sl)
types= first_sl->item_list;
else if (sl == first_sl)
{ {
if (is_recursive) if (is_recursive)
{ {
...@@ -846,6 +865,7 @@ bool st_select_lex_unit::prepare(THD *thd_arg, select_result *sel_result, ...@@ -846,6 +865,7 @@ bool st_select_lex_unit::prepare(THD *thd_arg, select_result *sel_result,
Item *type, *item_tmp; Item *type, *item_tmp;
while ((type= tp++, item_tmp= it++)) while ((type= tp++, item_tmp= it++))
{ {
DBUG_ASSERT(item_tmp->fixed);
if (((Item_type_holder*)type)->join_types(thd_arg, item_tmp)) if (((Item_type_holder*)type)->join_types(thd_arg, item_tmp))
DBUG_RETURN(TRUE); DBUG_RETURN(TRUE);
} }
...@@ -878,6 +898,7 @@ bool st_select_lex_unit::prepare(THD *thd_arg, select_result *sel_result, ...@@ -878,6 +898,7 @@ bool st_select_lex_unit::prepare(THD *thd_arg, select_result *sel_result,
} }
} }
cont:
/* /*
If the query is using select_union_direct, we have postponed If the query is using select_union_direct, we have postponed
preparation of the underlying select_result until column types preparation of the underlying select_result until column types
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment