mirror of
https://github.com/MariaDB/server.git
synced 2025-08-01 03:47:19 +03:00
MDEV-8199 - first_breadth_first_tab() takes 0.07% in OLTP RO
Split first_breadth_first_tab() into JOIN::first_breadth_first_optimization_tab() and JOIN::first_breadth_first_execution_tab(). This allows to eliminate function call and one condition. Adjusted callers accordingly. Overhead change: first_breadth_first_tab() 0.07% -> out of radar next_breadth_first_tab() 0.04% -> 0.04% JOIN::cleanup() 0.15% -> 0.11% JOIN::save_explain_data_intern() 0.28% -> 0.24%
This commit is contained in:
@ -277,7 +277,6 @@ JOIN_TAB *first_depth_first_tab(JOIN* join);
|
|||||||
JOIN_TAB *next_depth_first_tab(JOIN* join, JOIN_TAB* tab);
|
JOIN_TAB *next_depth_first_tab(JOIN* join, JOIN_TAB* tab);
|
||||||
|
|
||||||
enum enum_exec_or_opt {WALK_OPTIMIZATION_TABS , WALK_EXECUTION_TABS};
|
enum enum_exec_or_opt {WALK_OPTIMIZATION_TABS , WALK_EXECUTION_TABS};
|
||||||
JOIN_TAB *first_breadth_first_tab(JOIN *join, enum enum_exec_or_opt tabs_kind);
|
|
||||||
JOIN_TAB *next_breadth_first_tab(JOIN *join, enum enum_exec_or_opt tabs_kind,
|
JOIN_TAB *next_breadth_first_tab(JOIN *join, enum enum_exec_or_opt tabs_kind,
|
||||||
JOIN_TAB *tab);
|
JOIN_TAB *tab);
|
||||||
static double table_cond_selectivity(JOIN *join, uint idx, JOIN_TAB *s,
|
static double table_cond_selectivity(JOIN *join, uint idx, JOIN_TAB *s,
|
||||||
@ -7202,7 +7201,7 @@ double JOIN::get_examined_rows()
|
|||||||
{
|
{
|
||||||
double examined_rows;
|
double examined_rows;
|
||||||
double prev_fanout= 1;
|
double prev_fanout= 1;
|
||||||
JOIN_TAB *tab= first_breadth_first_tab(this, WALK_OPTIMIZATION_TABS);
|
JOIN_TAB *tab= first_breadth_first_optimization_tab();
|
||||||
JOIN_TAB *prev_tab= tab;
|
JOIN_TAB *prev_tab= tab;
|
||||||
|
|
||||||
examined_rows= tab->get_examined_rows();
|
examined_rows= tab->get_examined_rows();
|
||||||
@ -8201,21 +8200,23 @@ prev_record_reads(POSITION *positions, uint idx, table_map found_ref)
|
|||||||
Enumerate join tabs in breadth-first fashion, including const tables.
|
Enumerate join tabs in breadth-first fashion, including const tables.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
JOIN_TAB *first_breadth_first_tab(JOIN *join, enum enum_exec_or_opt tabs_kind)
|
|
||||||
{
|
|
||||||
/* There's always one (i.e. first) table */
|
|
||||||
return (tabs_kind == WALK_EXECUTION_TABS)? join->join_tab:
|
|
||||||
join->table_access_tabs;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
JOIN_TAB *next_breadth_first_tab(JOIN *join, enum enum_exec_or_opt tabs_kind,
|
JOIN_TAB *next_breadth_first_tab(JOIN *join, enum enum_exec_or_opt tabs_kind,
|
||||||
JOIN_TAB *tab)
|
JOIN_TAB *tab)
|
||||||
{
|
{
|
||||||
JOIN_TAB* const first_top_tab= first_breadth_first_tab(join, tabs_kind);
|
JOIN_TAB *first_top_tab;
|
||||||
const uint n_top_tabs_count= (tabs_kind == WALK_EXECUTION_TABS)?
|
uint n_top_tabs_count;
|
||||||
join->top_join_tab_count:
|
|
||||||
join->top_table_access_tabs_count;
|
if (tabs_kind == WALK_EXECUTION_TABS)
|
||||||
|
{
|
||||||
|
first_top_tab= join->first_breadth_first_execution_tab();
|
||||||
|
n_top_tabs_count= join->top_join_tab_count;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
first_top_tab= join->first_breadth_first_optimization_tab();
|
||||||
|
n_top_tabs_count= join->top_table_access_tabs_count;
|
||||||
|
}
|
||||||
|
|
||||||
if (!tab->bush_root_tab)
|
if (!tab->bush_root_tab)
|
||||||
{
|
{
|
||||||
/* We're at top level. Get the next top-level tab */
|
/* We're at top level. Get the next top-level tab */
|
||||||
@ -11800,27 +11801,19 @@ void JOIN::cleanup(bool full)
|
|||||||
w/o tables: they don't have some members initialized and
|
w/o tables: they don't have some members initialized and
|
||||||
WALK_OPTIMIZATION_TABS may not work correctly for them.
|
WALK_OPTIMIZATION_TABS may not work correctly for them.
|
||||||
*/
|
*/
|
||||||
enum enum_exec_or_opt tabs_kind;
|
|
||||||
if (first_breadth_first_tab(this, WALK_OPTIMIZATION_TABS))
|
|
||||||
tabs_kind= WALK_OPTIMIZATION_TABS;
|
|
||||||
else
|
|
||||||
tabs_kind= WALK_EXECUTION_TABS;
|
|
||||||
if (table_count)
|
if (table_count)
|
||||||
{
|
{
|
||||||
for (tab= first_breadth_first_tab(this, tabs_kind); tab;
|
for (tab= first_breadth_first_optimization_tab(); tab;
|
||||||
tab= next_breadth_first_tab(this, tabs_kind, tab))
|
tab= next_breadth_first_tab(this, WALK_OPTIMIZATION_TABS, tab))
|
||||||
{
|
|
||||||
tab->cleanup();
|
tab->cleanup();
|
||||||
}
|
|
||||||
|
|
||||||
if (tabs_kind == WALK_OPTIMIZATION_TABS &&
|
/* We've walked optimization tabs, do execution ones too. */
|
||||||
first_breadth_first_tab(this, WALK_OPTIMIZATION_TABS) !=
|
if (first_breadth_first_execution_tab() !=
|
||||||
first_breadth_first_tab(this, WALK_EXECUTION_TABS))
|
first_breadth_first_optimization_tab())
|
||||||
{
|
{
|
||||||
JOIN_TAB *jt= first_breadth_first_tab(this, WALK_EXECUTION_TABS);
|
for (tab= first_breadth_first_execution_tab(); tab;
|
||||||
/* We've walked optimization tabs. do execution ones too */
|
tab= next_breadth_first_tab(this, WALK_EXECUTION_TABS, tab))
|
||||||
if (jt)
|
tab->cleanup();
|
||||||
jt->cleanup();
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
cleaned= true;
|
cleaned= true;
|
||||||
@ -23556,13 +23549,13 @@ int append_possible_keys(MEM_ROOT *alloc, String_list &list, TABLE *table,
|
|||||||
|
|
||||||
void JOIN_TAB::update_explain_data(uint idx)
|
void JOIN_TAB::update_explain_data(uint idx)
|
||||||
{
|
{
|
||||||
if (this == first_breadth_first_tab(join, WALK_OPTIMIZATION_TABS) + join->const_tables &&
|
if (this == join->first_breadth_first_optimization_tab() + join->const_tables &&
|
||||||
join->select_lex->select_number != INT_MAX &&
|
join->select_lex->select_number != INT_MAX &&
|
||||||
join->select_lex->select_number != UINT_MAX)
|
join->select_lex->select_number != UINT_MAX)
|
||||||
{
|
{
|
||||||
Explain_table_access *eta= new (join->thd->mem_root) Explain_table_access(join->thd->mem_root);
|
Explain_table_access *eta= new (join->thd->mem_root) Explain_table_access(join->thd->mem_root);
|
||||||
JOIN_TAB* const first_top_tab= first_breadth_first_tab(join, WALK_OPTIMIZATION_TABS);
|
save_explain_data(eta, join->const_table_map, join->select_distinct,
|
||||||
save_explain_data(eta, join->const_table_map, join->select_distinct, first_top_tab);
|
join->first_breadth_first_optimization_tab());
|
||||||
|
|
||||||
Explain_select *sel= join->thd->lex->explain->get_select(join->select_lex->select_number);
|
Explain_select *sel= join->thd->lex->explain->get_select(join->select_lex->select_number);
|
||||||
idx -= my_count_bits(join->eliminated_tables);
|
idx -= my_count_bits(join->eliminated_tables);
|
||||||
@ -24059,7 +24052,7 @@ int JOIN::save_explain_data_intern(Explain_query *output, bool need_tmp_table,
|
|||||||
|
|
||||||
xpl_sel->exec_const_cond= exec_const_cond;
|
xpl_sel->exec_const_cond= exec_const_cond;
|
||||||
|
|
||||||
JOIN_TAB* const first_top_tab= first_breadth_first_tab(join, WALK_OPTIMIZATION_TABS);
|
JOIN_TAB* const first_top_tab= join->first_breadth_first_optimization_tab();
|
||||||
JOIN_TAB* prev_bush_root_tab= NULL;
|
JOIN_TAB* prev_bush_root_tab= NULL;
|
||||||
|
|
||||||
Explain_basic_join *cur_parent= xpl_sel;
|
Explain_basic_join *cur_parent= xpl_sel;
|
||||||
|
@ -1531,6 +1531,8 @@ public:
|
|||||||
int save_explain_data_intern(Explain_query *output, bool need_tmp_table,
|
int save_explain_data_intern(Explain_query *output, bool need_tmp_table,
|
||||||
bool need_order, bool distinct,
|
bool need_order, bool distinct,
|
||||||
const char *message);
|
const char *message);
|
||||||
|
JOIN_TAB *first_breadth_first_optimization_tab() { return table_access_tabs; }
|
||||||
|
JOIN_TAB *first_breadth_first_execution_tab() { return join_tab; }
|
||||||
private:
|
private:
|
||||||
/**
|
/**
|
||||||
TRUE if the query contains an aggregate function but has no GROUP
|
TRUE if the query contains an aggregate function but has no GROUP
|
||||||
|
Reference in New Issue
Block a user