Commit 7062a446 authored by unknown's avatar unknown

Merge gkodinov@bk-internal.mysql.com:/home/bk/mysql-5.0-opt

into  magare.gmz:/home/kgeorge/mysql/autopush/B27363-5.0-opt


mysql-test/r/subselect.result:
  Auto merged
mysql-test/t/subselect.test:
  Auto merged
sql/item.cc:
  Auto merged
sql/item_sum.cc:
  Auto merged
parents 209bf25a e14fd2b6
...@@ -4012,3 +4012,26 @@ WHERE (SELECT COUNT(t0.b) FROM t1 t WHERE t.b>20) GROUP BY a; ...@@ -4012,3 +4012,26 @@ WHERE (SELECT COUNT(t0.b) FROM t1 t WHERE t.b>20) GROUP BY a;
ERROR HY000: Invalid use of group function ERROR HY000: Invalid use of group function
SET @@sql_mode=default; SET @@sql_mode=default;
DROP TABLE t1; DROP TABLE t1;
CREATE TABLE t1 (a INT);
INSERT INTO t1 values (1),(1),(1),(1);
CREATE TABLE t2 (x INT);
INSERT INTO t1 values (1000),(1001),(1002);
SELECT SUM( (SELECT COUNT(a) FROM t2) ) FROM t1;
ERROR HY000: Invalid use of group function
SELECT SUM( (SELECT SUM(COUNT(a)) FROM t2) ) FROM t1;
ERROR HY000: Invalid use of group function
SELECT COUNT(1) FROM DUAL;
COUNT(1)
1
SELECT SUM( (SELECT AVG( (SELECT t1.a FROM t2) ) FROM DUAL) ) FROM t1;
ERROR HY000: Invalid use of group function
SELECT
SUM( (SELECT AVG( (SELECT COUNT(*) FROM t1 t HAVING t1.a < 12) ) FROM t2) )
FROM t1;
ERROR HY000: Invalid use of group function
SELECT t1.a as XXA,
SUM( (SELECT AVG( (SELECT COUNT(*) FROM t1 t HAVING XXA < 12) ) FROM t2) )
FROM t1;
ERROR HY000: Invalid use of group function
DROP TABLE t1,t2;
End of 5.0 tests.
...@@ -2845,3 +2845,33 @@ SELECT a FROM t1 t0 ...@@ -2845,3 +2845,33 @@ SELECT a FROM t1 t0
SET @@sql_mode=default; SET @@sql_mode=default;
DROP TABLE t1; DROP TABLE t1;
#
# Bug #27363: nested aggregates in outer, subquery / sum(select
# count(outer))
#
CREATE TABLE t1 (a INT); INSERT INTO t1 values (1),(1),(1),(1);
CREATE TABLE t2 (x INT); INSERT INTO t1 values (1000),(1001),(1002);
--error ER_INVALID_GROUP_FUNC_USE
SELECT SUM( (SELECT COUNT(a) FROM t2) ) FROM t1;
--error ER_INVALID_GROUP_FUNC_USE
SELECT SUM( (SELECT SUM(COUNT(a)) FROM t2) ) FROM t1;
SELECT COUNT(1) FROM DUAL;
--error ER_INVALID_GROUP_FUNC_USE
SELECT SUM( (SELECT AVG( (SELECT t1.a FROM t2) ) FROM DUAL) ) FROM t1;
--error ER_INVALID_GROUP_FUNC_USE
SELECT
SUM( (SELECT AVG( (SELECT COUNT(*) FROM t1 t HAVING t1.a < 12) ) FROM t2) )
FROM t1;
--error ER_INVALID_GROUP_FUNC_USE
SELECT t1.a as XXA,
SUM( (SELECT AVG( (SELECT COUNT(*) FROM t1 t HAVING XXA < 12) ) FROM t2) )
FROM t1;
DROP TABLE t1,t2;
--echo End of 5.0 tests.
...@@ -3521,9 +3521,13 @@ Item_field::fix_outer_field(THD *thd, Field **from_field, Item **reference) ...@@ -3521,9 +3521,13 @@ Item_field::fix_outer_field(THD *thd, Field **from_field, Item **reference)
select->inner_refs_list.push_back(rf); select->inner_refs_list.push_back(rf);
rf->in_sum_func= thd->lex->in_sum_func; rf->in_sum_func= thd->lex->in_sum_func;
} }
/*
A reference is resolved to a nest level that's outer or the same as
the nest level of the enclosing set function : adjust the value of
max_arg_level for the function if it's needed.
*/
if (thd->lex->in_sum_func && if (thd->lex->in_sum_func &&
thd->lex->in_sum_func->nest_level == thd->lex->in_sum_func->nest_level >= select->nest_level)
thd->lex->current_select->nest_level)
{ {
Item::Type ref_type= (*reference)->type(); Item::Type ref_type= (*reference)->type();
set_if_bigger(thd->lex->in_sum_func->max_arg_level, set_if_bigger(thd->lex->in_sum_func->max_arg_level,
...@@ -5174,6 +5178,16 @@ bool Item_ref::fix_fields(THD *thd, Item **reference) ...@@ -5174,6 +5178,16 @@ bool Item_ref::fix_fields(THD *thd, Item **reference)
thd->change_item_tree(reference, fld); thd->change_item_tree(reference, fld);
mark_as_dependent(thd, last_checked_context->select_lex, mark_as_dependent(thd, last_checked_context->select_lex,
thd->lex->current_select, this, fld); thd->lex->current_select, this, fld);
/*
A reference is resolved to a nest level that's outer or the same as
the nest level of the enclosing set function : adjust the value of
max_arg_level for the function if it's needed.
*/
if (thd->lex->in_sum_func &&
thd->lex->in_sum_func->nest_level >=
last_checked_context->select_lex->nest_level)
set_if_bigger(thd->lex->in_sum_func->max_arg_level,
last_checked_context->select_lex->nest_level);
return FALSE; return FALSE;
} }
if (ref == 0) if (ref == 0)
...@@ -5187,6 +5201,16 @@ bool Item_ref::fix_fields(THD *thd, Item **reference) ...@@ -5187,6 +5201,16 @@ bool Item_ref::fix_fields(THD *thd, Item **reference)
DBUG_ASSERT(*ref && (*ref)->fixed); DBUG_ASSERT(*ref && (*ref)->fixed);
mark_as_dependent(thd, last_checked_context->select_lex, mark_as_dependent(thd, last_checked_context->select_lex,
context->select_lex, this, this); context->select_lex, this, this);
/*
A reference is resolved to a nest level that's outer or the same as
the nest level of the enclosing set function : adjust the value of
max_arg_level for the function if it's needed.
*/
if (thd->lex->in_sum_func &&
thd->lex->in_sum_func->nest_level >=
last_checked_context->select_lex->nest_level)
set_if_bigger(thd->lex->in_sum_func->max_arg_level,
last_checked_context->select_lex->nest_level);
} }
} }
......
...@@ -175,13 +175,25 @@ bool Item_sum::check_sum_func(THD *thd, Item **ref) ...@@ -175,13 +175,25 @@ bool Item_sum::check_sum_func(THD *thd, Item **ref)
MYF(0)); MYF(0));
return TRUE; return TRUE;
} }
if (in_sum_func && in_sum_func->nest_level == nest_level) if (in_sum_func)
{ {
/* /*
If the set function is nested adjust the value of If the set function is nested adjust the value of
max_sum_func_level for the nesting set function. max_sum_func_level for the nesting set function.
We take into account only enclosed set functions that are to be
aggregated on the same level or above of the nest level of
the enclosing set function.
But we must always pass up the max_sum_func_level because it is
the maximum nested level of all directly and indirectly enclosed
set functions. We must do that even for set functions that are
aggregated inside of their enclosing set function's nest level
because the enclosing function may contain another enclosing
function that is to be aggregated outside or on the same level
as its parent's nest level.
*/ */
set_if_bigger(in_sum_func->max_sum_func_level, aggr_level); if (in_sum_func->nest_level >= aggr_level)
set_if_bigger(in_sum_func->max_sum_func_level, aggr_level);
set_if_bigger(in_sum_func->max_sum_func_level, max_sum_func_level);
} }
update_used_tables(); update_used_tables();
thd->lex->in_sum_func= in_sum_func; thd->lex->in_sum_func= in_sum_func;
......
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