mirror of
https://github.com/MariaDB/server.git
synced 2025-07-27 18:02:13 +03:00
MDEV-25128 Wrong result from join with materialized semi-join and
splittable derived If one of joined tables of the processed query is a materialized derived table (or view or CTE) with GROUP BY clause then under some conditions it can be subject to split optimization. With this optimization new equalities are injected into the WHERE condition of the SELECT that specifies this derived table. The injected equalities are generated for all join orders with which the split optimization can employed. After the best join order has been chosen only certain of this equalities are really needed. The others can be safely removed. If it's not done and some of injected equalities involve expressions over semi-joins with look-up access then the query may return a wrong result set. This patch effectively removes equalities injected for split optimization that are needed only at the optimization stage and not needed for execution. Approved by serg@mariadb.com
This commit is contained in:
@ -292,6 +292,8 @@ void set_postjoin_aggr_write_func(JOIN_TAB *tab);
|
||||
|
||||
static Item **get_sargable_cond(JOIN *join, TABLE *table);
|
||||
|
||||
bool is_eq_cond_injected_for_split_opt(Item_func_eq *eq_item);
|
||||
|
||||
#ifndef DBUG_OFF
|
||||
|
||||
/*
|
||||
@ -21787,6 +21789,21 @@ make_cond_for_table_from_pred(THD *thd, Item *root_cond, Item *cond,
|
||||
cond->marker=3; // Checked when read
|
||||
return (COND*) 0;
|
||||
}
|
||||
/*
|
||||
If cond is an equality injected for split optimization then
|
||||
a. when retain_ref_cond == false : cond is removed unconditionally
|
||||
(cond that supports ref access is removed by the preceding code)
|
||||
b. when retain_ref_cond == true : cond is removed if it does not
|
||||
support ref access
|
||||
*/
|
||||
if (left_item->type() == Item::FIELD_ITEM &&
|
||||
is_eq_cond_injected_for_split_opt((Item_func_eq *) cond) &&
|
||||
(!retain_ref_cond ||
|
||||
!test_if_ref(root_cond, (Item_field*) left_item,right_item)))
|
||||
{
|
||||
cond->marker=3;
|
||||
return (COND*) 0;
|
||||
}
|
||||
}
|
||||
cond->marker=2;
|
||||
cond->set_join_tab_idx(join_tab_idx_arg);
|
||||
|
Reference in New Issue
Block a user