mariadb/mysql-test/main/having_cond_pushdown.test
Igor Babaev 25870f48cf MDEV-18668 Server crash or ASAN use-after-poison in Item_equal_iterator /
st_select_lex::pushdown_from_having_into_where upon query
           with impossible WHERE condition

Do not push from HAVING into impossible WHERE
2019-02-24 02:02:07 -08:00

488 lines
11 KiB
Text

let $no_pushdown=
set statement optimizer_switch='condition_pushdown_from_having=off' for;
CREATE TABLE t1(a INT, b INT, c INT);
CREATE TABLE t2(x INT, y INT);
INSERT INTO t1 VALUES (1,14,3), (2,13,2), (1,22,1), (3,13,4), (3,14,2);
INSERT INTO t2 VALUES (2,13),(5,22),(3,14),(1,22);
CREATE VIEW v1
AS SELECT t1.a,MAX(t1.b),t1.c
FROM t1
GROUP BY t1.a;
CREATE FUNCTION f1() RETURNS INT RETURN 3;
--echo # conjunctive subformula
let $query=
SELECT t1.a,MAX(t1.b)
FROM t1
GROUP BY t1.a
HAVING (t1.a>2);
eval $no_pushdown $query;
eval $query;
eval explain $query;
eval explain format=json $query;
let $query=
SELECT t1.a,MAX(t1.b)
FROM t1
WHERE (t1.a>2)
GROUP BY t1.a;
eval $no_pushdown explain format=json $query;
--echo # conjunctive subformula : using equality
let $query=
SELECT t1.a,MAX(t1.b)
FROM t1
GROUP BY t1.a
HAVING (t1.a=2);
eval $no_pushdown $query;
eval $query;
eval explain $query;
eval explain format=json $query;
let $query=
SELECT t1.a,MAX(t1.b)
FROM t1
WHERE (t1.a=2)
GROUP BY t1.a;
eval $no_pushdown explain format=json $query;
--echo # extracted AND formula
let $query=
SELECT t1.a,MAX(t1.b)
FROM t1
GROUP BY t1.a
HAVING (t1.a>1) AND (t1.a<4);
eval $no_pushdown $query;
eval $query;
eval explain $query;
eval explain format=json $query;
let $query=
SELECT t1.a,MAX(t1.b)
FROM t1
WHERE (t1.a>1) AND (t1.a<4)
GROUP BY t1.a;
eval $no_pushdown explain format=json $query;
--echo # extracted OR formula
let $query=
SELECT t1.a,MAX(t1.b)
FROM t1
GROUP BY t1.a
HAVING (t1.a>1) OR (a IN (SELECT 3));
eval $no_pushdown $query;
eval $query;
eval explain $query;
eval explain format=json $query;
let $query=
SELECT t1.a,MAX(t1.b)
FROM t1
WHERE (t1.a>1) OR (a IN (SELECT 3))
GROUP BY t1.a;
eval $no_pushdown explain format=json $query;
let $query=
SELECT t1.a,MAX(t1.b),MIN(t1.c)
FROM t1
GROUP BY t1.a
HAVING ((t1.a>2) AND (MAX(t1.b)>13)) OR ((t1.a<3) AND (MIN(t1.c)>1));
eval $no_pushdown $query;
eval $query;
eval explain $query;
eval explain format=json $query;
let $query=
SELECT t1.a,MAX(t1.b),t1.c
FROM t1
WHERE (t1.a>2) OR (t1.a<3)
GROUP BY t1.a
HAVING ((t1.a>2) AND (MAX(t1.b)>13)) OR ((t1.a<3) AND (MIN(t1.c)>1));
eval $no_pushdown explain format=json $query;
--echo # conjunctive subformula : no aggregation formula pushdown
let $query=
SELECT t1.a,MAX(t1.b)
FROM t1
GROUP BY t1.a
HAVING (t1.a>1) AND (MAX(t1.a)<3);
eval $no_pushdown $query;
eval $query;
eval explain $query;
eval explain format=json $query;
let $query=
SELECT t1.a,MAX(t1.b)
FROM t1
WHERE (t1.a>1)
GROUP BY t1.a
HAVING (MAX(t1.a)<3);
eval $no_pushdown explain format=json $query;
let $query=
SELECT t1.a,MAX(t1.b)
FROM t1
GROUP BY t1.a
HAVING (t1.a>1) AND (MAX(t1.b)>13);
eval $no_pushdown $query;
eval $query;
eval explain $query;
eval explain format=json $query;
let $query=
SELECT t1.a,MAX(t1.b)
FROM t1
WHERE (t1.a>1)
GROUP BY t1.a
HAVING (MAX(t1.b)>13);
eval $no_pushdown explain format=json $query;
let $query=
SELECT t1.a,MAX(t1.b)
FROM t1
GROUP BY t1.a
HAVING (t1.a=3) AND (MAX(t1.a)=3);
eval $no_pushdown $query;
eval $query;
eval explain $query;
eval explain format=json $query;
let $query=
SELECT t1.a,MAX(t1.b)
FROM t1
WHERE (t1.a=3)
GROUP BY t1.a
HAVING (MAX(t1.a)=3);
eval $no_pushdown explain format=json $query;
let $query=
SELECT t1.a,MAX(t1.b)
FROM t1
GROUP BY t1.a
HAVING (t1.a=2) AND (MAX(t1.b)>12);
eval $no_pushdown $query;
eval $query;
eval explain $query;
eval explain format=json $query;
let $query=
SELECT t1.a,MAX(t1.b)
FROM t1
WHERE (t1.a=2)
GROUP BY t1.a
HAVING (MAX(t1.b)>12);
eval $no_pushdown explain format=json $query;
let $query=
SELECT t1.a,MAX(t1.b)
FROM t1
GROUP BY t1.a
HAVING (t1.a>1) AND (MAX(t1.b)=13);
eval $no_pushdown $query;
eval $query;
eval explain $query;
eval explain format=json $query;
let $query=
SELECT t1.a,MAX(t1.b)
FROM t1
WHERE (t1.a>1)
GROUP BY t1.a
HAVING (MAX(t1.b)=13);
eval $no_pushdown explain format=json $query;
let $query=
SELECT t1.a,MIN(t1.c)
FROM t1
GROUP BY t1.a
HAVING (t1.a>1) AND (MIN(t1.c)<3);
eval $no_pushdown $query;
eval $query;
eval explain $query;
eval explain format=json $query;
let $query=
SELECT t1.a,MIN(t1.c)
FROM t1
WHERE (t1.a>1)
GROUP BY t1.a
HAVING (MIN(t1.c)<3);
eval $no_pushdown explain format=json $query;
let $query=
SELECT t1.a,MAX(t1.b),MIN(t1.c)
FROM t1
GROUP BY t1.a
HAVING (t1.a=2) AND (MAX(t1.b)=13) AND (MIN(t1.c)=2);
eval $no_pushdown $query;
eval $query;
eval explain $query;
eval explain format=json $query;
let $query=
SELECT t1.a,MIN(t1.c)
FROM t1
WHERE (t1.a=2)
GROUP BY t1.a
HAVING (MAX(t1.b)=13) AND (MIN(t1.c)=2);
eval $no_pushdown explain format=json $query;
--echo # conjunctive subformula : no stored function pushdown
let $query=
SELECT t1.a,MAX(t1.b)
FROM t1
GROUP BY t1.a
HAVING (t1.a>1) AND (a=test.f1());
eval $no_pushdown $query;
eval $query;
eval explain $query;
eval explain format=json $query;
let $query=
SELECT t1.a,MAX(t1.b)
FROM t1
WHERE (t1.a>1)
GROUP BY t1.a
HAVING (a=test.f1());
eval $no_pushdown explain format=json $query;
--echo # conjunctive subformula : pushdown into derived table WHERE clause
let $query=
SELECT v1.a
FROM t2,v1
WHERE (t2.x=v1.a)
GROUP BY v1.a
HAVING (v1.a>1);
eval $no_pushdown $query;
eval $query;
eval explain $query;
eval explain format=json $query;
let $query=
SELECT v1.a
FROM t2,v1
WHERE (t2.x=v1.a) AND (v1.a>1)
GROUP BY v1.a;
eval $no_pushdown explain format=json $query;
--echo # conjunctive subformula : pushdown into derived table HAVING clause
let $query=
SELECT v1.a,v1.c
FROM t2,v1
WHERE (t2.x=v1.a)
GROUP BY v1.c
HAVING (v1.c>2);
eval $no_pushdown $query;
eval $query;
eval explain $query;
eval explain format=json $query;
let $query=
SELECT v1.a,v1.c
FROM t2,v1
WHERE (t2.x=v1.a) AND (v1.c>2)
GROUP BY v1.c;
eval $no_pushdown explain format=json $query;
--echo # conjunctive subformula : pushdown into materialized IN subquery
--echo # WHERE clause
let $query=
SELECT * FROM t1
WHERE
(t1.a,t1.b) IN (SELECT t2.x,MAX(t2.y) FROM t2 WHERE t2.x<5 GROUP BY t2.x)
GROUP BY t1.a
HAVING (t1.a>1);
eval $no_pushdown $query;
eval $query;
eval explain $query;
eval explain format=json $query;
let $query=
SELECT * FROM t1
WHERE
(t1.a>1) AND
(t1.a,t1.b) IN (SELECT t2.x,MAX(t2.y) FROM t2 WHERE t2.x<5 GROUP BY t2.x)
GROUP BY t1.a;
eval $no_pushdown explain format=json $query;
--echo # conjunctive subformula : pushdown into materialized IN subquery
--echo # HAVING clause
let $query=
SELECT * FROM t1
WHERE
(t1.a,t1.b) IN (SELECT t2.x,MAX(t2.y) FROM t2 WHERE t2.x<5 GROUP BY t2.x)
GROUP BY t1.b
HAVING (t1.b<14);
eval $no_pushdown $query;
eval $query;
eval explain $query;
eval explain format=json $query;
let $query=
SELECT * FROM t1
WHERE
(t1.b<14) AND
(t1.a,t1.b) IN (SELECT t2.x,MAX(t2.y) FROM t2 WHERE t2.x<5 GROUP BY t2.x)
GROUP BY t1.b;
eval $no_pushdown explain format=json $query;
--echo # non-standard allowed queries
--echo # conjunctive subformula
let $query=
SELECT t1.a,MAX(t1.b),t1.c
FROM t1
GROUP BY t1.a
HAVING (t1.c=2) AND (t1.a>1);
eval $no_pushdown $query;
eval $query;
eval explain $query;
eval explain format=json $query;
let $query=
SELECT t1.a,MAX(t1.b),t1.c FROM t1
WHERE (t1.a>1)
GROUP BY t1.a
HAVING (t1.c=2);
eval $no_pushdown explain format=json $query;
let $query=
SELECT MAX(t1.a),t1.a,t1.b,t1.c
FROM t1
GROUP BY t1.b
HAVING (t1.a=2) AND (t1.b=13) AND (t1.c=2);
eval $no_pushdown $query;
eval $query;
eval explain $query;
eval explain format=json $query;
let $query=
SELECT MAX(t1.a),t1.a,t1.b,t1.c
FROM t1
WHERE (t1.b=13)
GROUP BY t1.b
HAVING (t1.a=2) AND (t1.c=2);
eval $no_pushdown explain format=json $query;
--echo # extracted AND formula : using equalities
let $query=
SELECT t1.a,MAX(t1.b),t1.c
FROM t1
GROUP BY t1.a
HAVING (t1.a=t1.c) AND (t1.c>1);
eval $no_pushdown $query;
eval $query;
eval explain $query;
eval explain format=json $query;
let $query=
SELECT t1.a,MAX(t1.b) FROM t1
WHERE (t1.a=t1.c) AND (t1.a>1)
GROUP BY t1.a;
eval $no_pushdown explain format=json $query;
let $query=
SELECT t1.a,MAX(t1.b),t1.c
FROM t1
GROUP BY t1.a
HAVING (t1.a=t1.c) AND (t1.c=2);
eval $no_pushdown $query;
eval $query;
eval explain $query;
eval explain format=json $query;
let $query=
SELECT t1.a,MAX(t1.b),t1.c
FROM t1
WHERE (t1.a=t1.c) AND (t1.a=2)
GROUP BY t1.a;
eval $no_pushdown explain format=json $query;
let $query=
SELECT t1.a,MAX(t1.b),t1.c
FROM t1
GROUP BY t1.a
HAVING ((t1.a=t1.c) AND (t1.a>1)) OR ((t1.a<3) AND (t1.c>3));
eval $no_pushdown $query;
eval $query;
eval explain $query;
eval explain format=json $query;
let $query=
SELECT t1.a,MAX(t1.b),t1.c
FROM t1
WHERE ((t1.a=t1.c) AND (t1.a>1)) OR (t1.a<3)
GROUP BY t1.a
HAVING ((t1.a=t1.c) AND (t1.a>1)) OR ((t1.a<3) AND (t1.c>3));
eval $no_pushdown explain format=json $query;
--echo # conjuctive subformula : pushdown using WHERE multiple equalities
let $query=
SELECT t1.a,MAX(t1.b),t1.c
FROM t1
WHERE (t1.a=t1.c)
GROUP BY t1.a
HAVING (t1.c<3);
eval $no_pushdown $query;
eval $query;
eval explain $query;
eval explain format=json $query;
let $query=
SELECT t1.a,MAX(t1.b),t1.c
FROM t1
WHERE (t1.a=t1.c) AND (t1.c<3)
GROUP BY t1.a;
eval $no_pushdown explain format=json $query;
--echo # extracted AND-formula : pushdown using WHERE multiple equalities
let $query=
SELECT t1.a,MAX(t1.b),t1.c
FROM t1
WHERE (t1.a=t1.c)
GROUP BY t1.a
HAVING (t1.a>1) AND (t1.c<3);
eval $no_pushdown $query;
eval $query;
eval explain $query;
eval explain format=json $query;
let $query=
SELECT t1.a,MAX(t1.b),t1.c
FROM t1
WHERE (t1.a=t1.c) AND (t1.a>1) AND (t1.c<3)
GROUP BY t1.a;
eval $no_pushdown explain format=json $query;
let $query=
SELECT t1.a,MAX(t1.b),t1.c
FROM t1
WHERE (t1.a=t1.c)
GROUP BY t1.a
HAVING (((t1.a>1) AND (MAX(t1.c)<3)) OR (t1.c<4)) AND (t1.a<2);
eval $no_pushdown $query;
eval $query;
eval explain $query;
eval explain format=json $query;
let $query=
SELECT t1.a,MAX(t1.b),t1.c
FROM t1
WHERE (t1.a=t1.c) AND (((t1.a>1) OR (t1.c<4)) AND (t1.a<2))
GROUP BY t1.a
HAVING ((t1.a>1) AND (MAX(t1.c)<3)) OR (t1.c<4);
eval $no_pushdown explain format=json $query;
--echo # extracted OR-formula : pushdown using WHERE multiple equalities
let $query=
SELECT t1.a,MAX(t1.b),t1.c
FROM t1
WHERE (t1.a=t1.c)
GROUP BY t1.a
HAVING ((t1.a>1) AND (MAX(t1.c)<3)) OR (t1.c<4);
eval $no_pushdown $query;
eval $query;
eval explain $query;
eval explain format=json $query;
let $query=
SELECT t1.a,MAX(t1.b),t1.c
FROM t1
WHERE (t1.a=t1.c) AND ((t1.a>1) OR (t1.c<4))
GROUP BY t1.a
HAVING ((t1.a>1) AND (MAX(t1.c)<3)) OR (t1.c<4);
eval $no_pushdown explain format=json $query;
DROP TABLE t1,t2;
DROP VIEW v1;
DROP FUNCTION f1;
--echo #
--echo # MDEV-18668: pushdown from HAVING into impossible WHERE
--echo #
CREATE TABLE t1 (a INT, b INT);
INSERT INTO t1 VALUES (1,1),(2,2);
SELECT a FROM t1 WHERE b = 1 AND b = 2 GROUP BY a HAVING a <= 3;
EXPLAIN
SELECT a FROM t1 WHERE b = 1 AND b = 2 GROUP BY a HAVING a <= 3;
DROP TABLE t1;