Skip to content
/ server Public
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
6 changes: 6 additions & 0 deletions mysql-test/main/subselect4.result
Original file line number Diff line number Diff line change
Expand Up @@ -3372,6 +3372,12 @@ drop table t1,t2,t3;
CREATE TABLE t(c INT);
SELECT (SELECT 0 GROUP BY c HAVING (SELECT c)) FROM t GROUP BY c;
(SELECT 0 GROUP BY c HAVING (SELECT c))
#
# MDEV-31632 Unresolvable outer reference causes null pointer exception
#
SELECT 1 union select 2 UNION SELECT 1 from t JOIN t b ON
(SELECT 1 FROM dual WHERE AAA);
ERROR 42S22: Unknown column 'AAA' in 'WHERE'
DROP TABLE t;
#
# MDEV-38476 Wrong Result (Empty Set) with derived_merge=on using AVG() on text column in HAVING clause
Expand Down
9 changes: 9 additions & 0 deletions mysql-test/main/subselect4.test
Original file line number Diff line number Diff line change
Expand Up @@ -2693,6 +2693,15 @@ drop table t1,t2,t3;

CREATE TABLE t(c INT);
SELECT (SELECT 0 GROUP BY c HAVING (SELECT c)) FROM t GROUP BY c;

--echo #
--echo # MDEV-31632 Unresolvable outer reference causes null pointer exception
--echo #

--error ER_BAD_FIELD_ERROR
SELECT 1 union select 2 UNION SELECT 1 from t JOIN t b ON
(SELECT 1 FROM dual WHERE AAA);

DROP TABLE t;

--echo #
Expand Down
30 changes: 23 additions & 7 deletions sql/item.cc
Original file line number Diff line number Diff line change
Expand Up @@ -5920,10 +5920,19 @@ Item_field::fix_outer_field(THD *thd, Field **from_field, Item **reference)
select= outer_context->select_lex;
Item_subselect *prev_subselect_item=
last_checked_context->select_lex->master_unit()->item;
/*
We have merged to the top select and this field is no longer outer,
or we have reached the outermost select without resolution
*/
bool at_top= !prev_subselect_item;
last_checked_context= outer_context;
upward_lookup= TRUE;

place= prev_subselect_item->parsing_place;
if (!at_top)
place= prev_subselect_item->parsing_place;
else
place= NO_MATTER;

/*
If outer_field is set, field was already found by first call
to find_field_in_tables(). Only need to find appropriate context.
Expand Down Expand Up @@ -5978,8 +5987,11 @@ Item_field::fix_outer_field(THD *thd, Field **from_field, Item **reference)
}
if (*from_field != view_ref_found)
{
prev_subselect_item->used_tables_cache|= (*from_field)->table->map;
prev_subselect_item->const_item_cache= 0;
if (!at_top)
{
prev_subselect_item->used_tables_cache|= (*from_field)->table->map;
prev_subselect_item->const_item_cache= 0;
}
set_field(*from_field);
if (!last_checked_context->select_lex->having_fix_field &&
select->group_list.elements &&
Expand Down Expand Up @@ -6028,7 +6040,8 @@ Item_field::fix_outer_field(THD *thd, Field **from_field, Item **reference)
else
{
Item::Type ref_type= (*reference)->type();
prev_subselect_item->used_tables_and_const_cache_join(*reference);
if (!at_top)
prev_subselect_item->used_tables_and_const_cache_join(*reference);
mark_as_dependent(thd, last_checked_context->select_lex,
context->select_lex, this,
((ref_type == REF_ITEM || ref_type == FIELD_ITEM) ?
Expand Down Expand Up @@ -6076,7 +6089,7 @@ Item_field::fix_outer_field(THD *thd, Field **from_field, Item **reference)
if (refref->fixed())
(*ref)->fix_fields_if_needed( thd, reference);
}
if ((*ref)->fixed())
if (!at_top && (*ref)->fixed())
prev_subselect_item->used_tables_and_const_cache_join(*ref);

break;
Expand All @@ -6088,8 +6101,11 @@ Item_field::fix_outer_field(THD *thd, Field **from_field, Item **reference)
outer select (or we just trying to find wrong identifier, in this
case it does not matter which used tables bits we set)
*/
prev_subselect_item->used_tables_cache|= OUTER_REF_TABLE_BIT;
prev_subselect_item->const_item_cache= 0;
if (!at_top)
{
prev_subselect_item->used_tables_cache|= OUTER_REF_TABLE_BIT;
prev_subselect_item->const_item_cache= 0;
}
}

DBUG_ASSERT(ref != 0);
Expand Down