diff options
Diffstat (limited to 'sql/sql_lex.cc')
-rw-r--r-- | sql/sql_lex.cc | 67 |
1 files changed, 62 insertions, 5 deletions
diff --git a/sql/sql_lex.cc b/sql/sql_lex.cc index a6494c72889..9aee5caeb64 100644 --- a/sql/sql_lex.cc +++ b/sql/sql_lex.cc @@ -1640,7 +1640,8 @@ void st_select_lex::init_query() link_next= 0; lock_option= TL_READ_DEFAULT; is_prep_leaf_list_saved= FALSE; - + + have_merged_subqueries= FALSE; bzero((char*) expr_cache_may_be_used, sizeof(expr_cache_may_be_used)); } @@ -3119,7 +3120,7 @@ bool st_select_lex::optimize_unflattened_subqueries() if (options & SELECT_DESCRIBE) { /* Optimize the subquery in the context of EXPLAIN. */ - sl->set_explain_type(); + sl->set_explain_type(FALSE); sl->options|= SELECT_DESCRIBE; inner_join->select_options|= SELECT_DESCRIBE; } @@ -3501,7 +3502,7 @@ void SELECT_LEX::update_used_tables() Set the EXPLAIN type for this subquery. */ -void st_select_lex::set_explain_type() +void st_select_lex::set_explain_type(bool on_the_fly) { bool is_primary= FALSE; if (next_select()) @@ -3523,6 +3524,9 @@ void st_select_lex::set_explain_type() } } + if (on_the_fly && !is_primary && have_merged_subqueries) + is_primary= TRUE; + SELECT_LEX *first= master_unit()->first_select(); /* drop UNCACHEABLE_EXPLAIN, because it is for internal usage only */ uint8 is_uncacheable= (uncacheable & ~UNCACHEABLE_EXPLAIN); @@ -3539,8 +3543,13 @@ void st_select_lex::set_explain_type() ((is_uncacheable & UNCACHEABLE_DEPENDENT) ? "DEPENDENT UNION": is_uncacheable ? "UNCACHEABLE UNION": - "UNION"))); - options|= SELECT_DESCRIBE; + (this == master_unit()->fake_select_lex)? "UNION RESULT" : "UNION"))); + + if (this == master_unit()->fake_select_lex) + type= "UNION RESULT"; + + if (!on_the_fly) + options|= SELECT_DESCRIBE; } @@ -3687,6 +3696,54 @@ bool st_select_lex::is_merged_child_of(st_select_lex *ancestor) } +int st_select_lex::print_explain(select_result_sink *output) +{ + int res; + if (join && join->optimized == 2) + { + res= join->print_explain(output, TRUE, + FALSE, // need_tmp_table, + FALSE, // bool need_order, + FALSE, // bool distinct, + NULL); //const char *message + } + else + { + /* Produce "not yet optimized" line */ + const char *msg="Not yet optimized"; + res= join->print_explain(output, TRUE, + FALSE, // need_tmp_table, + FALSE, // bool need_order, + FALSE, // bool distinct, + msg); //const char *message + } + return 0; +} + + +int st_select_lex_unit::print_explain(select_result_sink *output) +{ + int res= 0; + SELECT_LEX *first= first_select(); + + for (SELECT_LEX *sl= first; sl; sl= sl->next_select()) + { + if ((res= sl->print_explain(output))) + break; + } + + /* + Note: it could be that fake_select_lex->join == NULL still at this point + */ + if (fake_select_lex && !fake_select_lex->join) + { + res= print_fake_select_lex_join(output, TRUE /* on the fly */, + fake_select_lex, 0 /* flags */); + } + return res; +} + + /** A routine used by the parser to decide whether we are specifying a full partitioning or if only partitions to add or to split. |