@@ -12776,7 +12776,8 @@ bool Item_func_eq::check_equality(THD *thd, COND_EQUAL *cond_equal,
12776
12776
12777
12777
COND *Item_cond_and::build_equal_items(THD *thd,
12778
12778
COND_EQUAL *inherited,
12779
- bool link_item_fields)
12779
+ bool link_item_fields,
12780
+ COND_EQUAL **cond_equal_ref)
12780
12781
{
12781
12782
Item_equal *item_equal;
12782
12783
COND_EQUAL cond_equal;
@@ -12788,6 +12789,7 @@ COND *Item_cond_and::build_equal_items(THD *thd,
12788
12789
List_iterator<Item> li(*args);
12789
12790
Item *item;
12790
12791
12792
+ DBUG_ASSERT(!cond_equal_ref || !cond_equal_ref[0]);
12791
12793
/*
12792
12794
Retrieve all conjuncts of this level detecting the equality
12793
12795
that are subject to substitution by multiple equality items and
@@ -12812,7 +12814,7 @@ COND *Item_cond_and::build_equal_items(THD *thd,
12812
12814
if (!args->elements &&
12813
12815
!cond_equal.current_level.elements &&
12814
12816
!eq_list.elements)
12815
- return new Item_int((longlong) 1, 1);
12817
+ return new (thd->mem_root) Item_int((longlong) 1, 1);
12816
12818
12817
12819
List_iterator_fast<Item_equal> it(cond_equal.current_level);
12818
12820
while ((item_equal= it++))
@@ -12836,7 +12838,7 @@ COND *Item_cond_and::build_equal_items(THD *thd,
12836
12838
while ((item= li++))
12837
12839
{
12838
12840
Item *new_item;
12839
- if ((new_item= item->build_equal_items(thd, inherited, FALSE ))
12841
+ if ((new_item= item->build_equal_items(thd, inherited, false, NULL ))
12840
12842
!= item)
12841
12843
{
12842
12844
/* This replacement happens only for standalone equalities */
@@ -12851,19 +12853,23 @@ COND *Item_cond_and::build_equal_items(THD *thd,
12851
12853
args->append(&eq_list);
12852
12854
args->append((List<Item> *)&cond_equal.current_level);
12853
12855
update_used_tables();
12856
+ if (cond_equal_ref)
12857
+ *cond_equal_ref= &m_cond_equal;
12854
12858
return this;
12855
12859
}
12856
12860
12857
12861
12858
12862
COND *Item_cond::build_equal_items(THD *thd,
12859
12863
COND_EQUAL *inherited,
12860
- bool link_item_fields)
12864
+ bool link_item_fields,
12865
+ COND_EQUAL **cond_equal_ref)
12861
12866
{
12862
12867
List<Item> *args= argument_list();
12863
12868
12864
12869
List_iterator<Item> li(*args);
12865
12870
Item *item;
12866
12871
12872
+ DBUG_ASSERT(!cond_equal_ref || !cond_equal_ref[0]);
12867
12873
/*
12868
12874
Make replacement of equality predicates for lower levels
12869
12875
of the condition expression.
@@ -12873,7 +12879,7 @@ COND *Item_cond::build_equal_items(THD *thd,
12873
12879
while ((item= li++))
12874
12880
{
12875
12881
Item *new_item;
12876
- if ((new_item= item->build_equal_items(thd, inherited, FALSE ))
12882
+ if ((new_item= item->build_equal_items(thd, inherited, false, NULL ))
12877
12883
!= item)
12878
12884
{
12879
12885
/* This replacement happens only for standalone equalities */
@@ -12892,11 +12898,14 @@ COND *Item_cond::build_equal_items(THD *thd,
12892
12898
12893
12899
COND *Item_func_eq::build_equal_items(THD *thd,
12894
12900
COND_EQUAL *inherited,
12895
- bool link_item_fields)
12901
+ bool link_item_fields,
12902
+ COND_EQUAL **cond_equal_ref)
12896
12903
{
12897
12904
COND_EQUAL cond_equal;
12898
12905
cond_equal.upper_levels= inherited;
12899
12906
List<Item> eq_list;
12907
+
12908
+ DBUG_ASSERT(!cond_equal_ref || !cond_equal_ref[0]);
12900
12909
/*
12901
12910
If an equality predicate forms the whole and level,
12902
12911
we call it standalone equality and it's processed here.
@@ -12912,7 +12921,7 @@ COND *Item_func_eq::build_equal_items(THD *thd,
12912
12921
Item_equal *item_equal;
12913
12922
int n= cond_equal.current_level.elements + eq_list.elements;
12914
12923
if (n == 0)
12915
- return new Item_int((longlong) 1,1);
12924
+ return new (thd->mem_root) Item_int((longlong) 1,1);
12916
12925
else if (n == 1)
12917
12926
{
12918
12927
if ((item_equal= cond_equal.current_level.pop()))
@@ -12922,10 +12931,14 @@ COND *Item_func_eq::build_equal_items(THD *thd,
12922
12931
set_if_bigger(thd->lex->current_select->max_equal_elems,
12923
12932
item_equal->n_field_items());
12924
12933
item_equal->upper_levels= inherited;
12934
+ if (cond_equal_ref)
12935
+ *cond_equal_ref= new (thd->mem_root) COND_EQUAL(item_equal,
12936
+ thd->mem_root);
12925
12937
return item_equal;
12926
12938
}
12927
12939
Item *res= eq_list.pop();
12928
12940
res->update_used_tables();
12941
+ DBUG_ASSERT(res->type() == FUNC_ITEM);
12929
12942
return res;
12930
12943
}
12931
12944
else
@@ -12949,15 +12962,19 @@ COND *Item_func_eq::build_equal_items(THD *thd,
12949
12962
cond_equal.current_level= and_cond->m_cond_equal.current_level;
12950
12963
args->append((List<Item> *)&cond_equal.current_level);
12951
12964
and_cond->update_used_tables();
12965
+ if (cond_equal_ref)
12966
+ *cond_equal_ref= &and_cond->m_cond_equal;
12952
12967
return and_cond;
12953
12968
}
12954
12969
}
12955
- return Item_func::build_equal_items(thd, inherited, link_item_fields);
12970
+ return Item_func::build_equal_items(thd, inherited, link_item_fields,
12971
+ cond_equal_ref);
12956
12972
}
12957
12973
12958
12974
12959
12975
COND *Item_func::build_equal_items(THD *thd, COND_EQUAL *inherited,
12960
- bool link_item_fields)
12976
+ bool link_item_fields,
12977
+ COND_EQUAL **cond_equal_ref)
12961
12978
{
12962
12979
/*
12963
12980
For each field reference in cond, not from equal item predicates,
@@ -12971,6 +12988,20 @@ COND *Item_func::build_equal_items(THD *thd, COND_EQUAL *inherited,
12971
12988
&Item::equal_fields_propagator,
12972
12989
(uchar *) inherited);
12973
12990
cond->update_used_tables();
12991
+ DBUG_ASSERT(cond == this);
12992
+ DBUG_ASSERT(!cond_equal_ref || !cond_equal_ref[0]);
12993
+ return cond;
12994
+ }
12995
+
12996
+
12997
+ COND *Item_equal::build_equal_items(THD *thd, COND_EQUAL *inherited,
12998
+ bool link_item_fields,
12999
+ COND_EQUAL **cond_equal_ref)
13000
+ {
13001
+ COND *cond= Item_func::build_equal_items(thd, inherited, link_item_fields,
13002
+ cond_equal_ref);
13003
+ if (cond_equal_ref)
13004
+ *cond_equal_ref= new (thd->mem_root) COND_EQUAL(this, thd->mem_root);
12974
13005
return cond;
12975
13006
}
12976
13007
@@ -13052,28 +13083,19 @@ static COND *build_equal_items(JOIN *join, COND *cond,
13052
13083
bool link_equal_fields)
13053
13084
{
13054
13085
THD *thd= join->thd;
13055
- COND_EQUAL *cond_equal= 0;
13086
+
13087
+ *cond_equal_ref= NULL;
13056
13088
13057
13089
if (cond)
13058
13090
{
13059
- cond= cond->build_equal_items(thd, inherited, link_equal_fields);
13060
- if (cond->type() == Item::COND_ITEM &&
13061
- ((Item_cond*) cond)->functype() == Item_func::COND_AND_FUNC)
13062
- cond_equal= &((Item_cond_and*) cond)->m_cond_equal;
13063
-
13064
- else if (cond->type() == Item::FUNC_ITEM &&
13065
- ((Item_cond*) cond)->functype() == Item_func::MULT_EQUAL_FUNC)
13091
+ cond= cond->build_equal_items(thd, inherited, link_equal_fields,
13092
+ cond_equal_ref);
13093
+ if (*cond_equal_ref)
13066
13094
{
13067
- cond_equal= new (thd->mem_root) COND_EQUAL ;
13068
- cond_equal->current_level.push_back((Item_equal *) cond, thd->mem_root) ;
13095
+ (*cond_equal_ref)->upper_levels= inherited ;
13096
+ inherited= *cond_equal_ref ;
13069
13097
}
13070
13098
}
13071
- if (cond_equal)
13072
- {
13073
- cond_equal->upper_levels= inherited;
13074
- inherited= cond_equal;
13075
- }
13076
- *cond_equal_ref= cond_equal;
13077
13099
13078
13100
if (join_list && !ignore_on_conds)
13079
13101
{
0 commit comments