Commit e7f289c5 authored by Varun Gupta's avatar Varun Gupta

MDEV-23646: Optimizer trace: optimize_cond() should show ON expression processing

Print in the optimizer trace equality and constant propagation of the ON expression
parent edb5ae00
This diff is collapsed.
......@@ -642,6 +642,12 @@ where t1.a = t2.a;
SELECT JSON_DETAILED(JSON_EXTRACT(trace, '$**.where_clause_after_substitution')) from INFORMATION_SCHEMA.OPTIMIZER_TRACE;
SELECT JSON_DETAILED(JSON_EXTRACT(trace, '$**.having_clause_after_substitution')) from INFORMATION_SCHEMA.OPTIMIZER_TRACE;
SELECT JSON_DETAILED(JSON_EXTRACT(trace, '$**.on_clause_after_substitution')) from INFORMATION_SCHEMA.OPTIMIZER_TRACE;
--echo #
--echo # MDEV-23646: Optimizer trace: optimize_cond() should show ON expression processing
--echo #
SELECT JSON_DETAILED(JSON_EXTRACT(trace, '$**.condition_processing')) from INFORMATION_SCHEMA.OPTIMIZER_TRACE;
DROP TABLE t1,t2,t3;
set optimizer_trace='enabled=off';
......
......@@ -53,6 +53,13 @@ explain select * from t1 where a=1 or b=1 {
]
}
},
{
"condition_processing": {
"condition": "ON CLAUSE",
"original_expr": [],
"transformed_expr": []
}
},
{
"table_dependencies": [
{
......
......@@ -61,6 +61,13 @@ explain select * from t1 where pk1 != 0 and key1 = 1 {
]
}
},
{
"condition_processing": {
"condition": "ON CLAUSE",
"original_expr": [],
"transformed_expr": []
}
},
{
"table_dependencies": [
{
......
......@@ -64,6 +64,13 @@ select * from db1.t1 {
"join_optimization": {
"select_id": 1,
"steps": [
{
"condition_processing": {
"condition": "ON CLAUSE",
"original_expr": [],
"transformed_expr": []
}
},
{
"table_dependencies": [
{
......@@ -192,6 +199,13 @@ select * from db1.v1 {
"join_optimization": {
"select_id": 1,
"steps": [
{
"condition_processing": {
"condition": "ON CLAUSE",
"original_expr": [],
"transformed_expr": []
}
},
{
"table_dependencies": [
{
......
......@@ -339,10 +339,10 @@ where t1.a = t2.a and ( t1.a = ( select min(a) from t1 ) or 0 );
id select_type table type possible_keys key key_len ref rows filtered Extra
1 PRIMARY t1 ALL NULL NULL NULL NULL 2 100.00 Using where
1 PRIMARY t2 ALL NULL NULL NULL NULL 3 100.00 Using where; Using join buffer (flat, BNL join)
1 PRIMARY t3 ref idx idx 6 func 2 100.00 Using where; Using index
1 PRIMARY t3 ref idx idx 6 const 1 100.00 Using where; Using index
2 SUBQUERY t1 ALL NULL NULL NULL NULL 2 100.00
Warnings:
Note 1003 /* select#1 */ select `test`.`t1`.`a` AS `a`,`test`.`t2`.`a` AS `a`,`test`.`t3`.`a` AS `a` from `test`.`t1` join `test`.`t2` left join `test`.`t3` on(`test`.`t3`.`a` = `test`.`t1`.`a`) where `test`.`t1`.`a` = (/* select#2 */ select min(`test`.`t1`.`a`) from `test`.`t1`) and `test`.`t2`.`a` = (/* select#2 */ select min(`test`.`t1`.`a`) from `test`.`t1`)
Note 1003 /* select#1 */ select `test`.`t1`.`a` AS `a`,`test`.`t2`.`a` AS `a`,`test`.`t3`.`a` AS `a` from `test`.`t1` join `test`.`t2` left join `test`.`t3` on(`test`.`t3`.`a` = (/* select#2 */ select min(`test`.`t1`.`a`) from `test`.`t1`)) where `test`.`t1`.`a` = (/* select#2 */ select min(`test`.`t1`.`a`) from `test`.`t1`) and `test`.`t2`.`a` = (/* select#2 */ select min(`test`.`t1`.`a`) from `test`.`t1`)
select * from t1, t2 left join t3 on ( t2.a = t3.a )
where t1.a = t2.a and ( t1.a = ( select min(a) from t1 ) or 0 );
a a a
......
......@@ -689,6 +689,28 @@ void print_on_expr(JOIN *join, Json_writer_array *trace_on_expr)
}
void print_on_expr(THD *thd, List<TABLE_LIST> *join_list,
Json_writer_array *trace_array)
{
if (join_list == NULL)
return;
TABLE_LIST *table;
List_iterator<TABLE_LIST> li(*join_list);
while ((table= li++))
{
if (table->on_expr)
{
List<TABLE_LIST> *nested_join_list= table->nested_join ?
&table->nested_join->join_list : NULL;
trace_array->add(table->on_expr);
print_on_expr(thd, nested_join_list, trace_array);
}
}
}
/*
Introduce enum_query_type flags parameter, maybe also allow
EXPLAIN also use this function.
......
......@@ -108,6 +108,8 @@ void print_final_join_order(JOIN *join);
void print_best_access_for_table(THD *thd, POSITION *pos,
enum join_type type);
void print_on_expr(JOIN *join, Json_writer_array *trace_on_expr);
void print_on_expr(THD *thd, List<TABLE_LIST> *join_list,
Json_writer_array *trace_array);
/*
Security related (need to add a proper comment here)
*/
......
......@@ -170,6 +170,12 @@ static COND *optimize_cond(JOIN *join, COND *conds,
Item::cond_result *cond_value,
COND_EQUAL **cond_equal,
int flags= 0);
static void optimize_on_expr(JOIN *join,
List<TABLE_LIST> *join_list,
bool ignore_on_conds,
int flags= 0);
bool const_expression_in_where(COND *conds,Item *item, Item **comp_item);
static int do_select(JOIN *join, Procedure *procedure);
......@@ -2014,9 +2020,11 @@ JOIN::optimize_inner()
ignore_on_expr= true;
break;
}
conds= optimize_cond(this, conds, join_list, ignore_on_expr,
conds= optimize_cond(this, conds, join_list, TRUE,
&cond_value, &cond_equal, OPT_LINK_EQUAL_FIELDS);
optimize_on_expr(this, join_list, ignore_on_expr);
if (thd->is_error())
{
error= 1;
......@@ -2472,11 +2480,19 @@ int JOIN::optimize_stage2()
if (unlikely(thd->trace_started()))
{
Json_writer_object trace_wrapper(thd);
trace_wrapper.add("where_clause_after_substitution", conds);
trace_wrapper.add("having_clause_after_substitution", having);
Json_writer_array trace_on_expr(thd, "on_clause_after_substitution");
print_on_expr(this, &trace_on_expr);
if (having || conds || outer_join)
{
Json_writer_object trace_wrapper(thd);
if (conds)
trace_wrapper.add("where_clause_after_substitution", conds);
if (having)
trace_wrapper.add("having_clause_after_substitution", having);
if (outer_join)
{
Json_writer_array trace_on_expr(thd, "on_clause_after_substitution");
print_on_expr(this, &trace_on_expr);
}
}
}
/*
......@@ -17007,6 +17023,52 @@ optimize_cond(JOIN *join, COND *conds,
}
static void optimize_on_expr(JOIN *join,
List<TABLE_LIST> *join_list,
bool ignore_on_conds,
int flags)
{
if (ignore_on_conds || !join_list)
return;
THD *thd= join->thd;
Json_writer_object trace_wrapper(thd);
Json_writer_object trace_cond(thd, "condition_processing");
trace_cond.add("condition", "ON CLAUSE");
{
Json_writer_array trace_array(thd, "original_expr");
print_on_expr(thd, join_list, &trace_array);
}
if (join_list && !ignore_on_conds)
{
TABLE_LIST *table;
List_iterator<TABLE_LIST> li(*join_list);
while ((table= li++))
{
if (table->on_expr)
{
List<TABLE_LIST> *nested_join_list= table->nested_join ?
&table->nested_join->join_list : NULL;
/*
We can modify table->on_expr because its old value will
be restored before re-execution of PS/SP.
*/
table->on_expr= build_equal_items(join, table->on_expr, join->cond_equal,
nested_join_list, ignore_on_conds,
&table->cond_equal);
}
}
}
{
Json_writer_array trace_array(thd, "transformed_expr");
print_on_expr(thd, join_list, &trace_array);
}
}
/**
@brief
Propagate multiple equalities to the sub-expressions of a condition
......
......@@ -2638,7 +2638,7 @@ static Sys_var_flagset Sys_optimizer_trace(
" {enabled}"
" and val is one of {on, off, default}",
SESSION_VAR(optimizer_trace), CMD_LINE(REQUIRED_ARG),
Opt_trace_context::flag_names, DEFAULT(Opt_trace_context::FLAG_DEFAULT));
Opt_trace_context::flag_names, DEFAULT(Opt_trace_context::FLAG_ENABLED));
// @see set_var::is_var_optimizer_trace()
export sys_var *Sys_optimizer_trace_ptr = &Sys_optimizer_trace;
......
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