Commit 9fde2bba authored by Igor Babaev's avatar Igor Babaev

MDEV-25484 Crash when parsing query using derived table containing TVC

This patch fixes parsing problems concerning derived tables that use table
value constructors (TVC) with LIMIT and ORDER BY clauses of the form
  ((VALUES ... LIMIT ...) ORDER BY ...) as dt
The fix has to be applied only to 10.3 as 10.4 that employs a different
grammar rules has no such problems. The test cases should be merged
upstream.

Approved by Oleksandr Byelkin <sanja@mariadb.com>
parent 73d32cc1
......@@ -3062,4 +3062,42 @@ a
2
3
drop table t1;
#
# MDEV-25484: Derived table using TVC with LIMIT and ORDER BY
#
create table t1 (a int);
insert into t1 values (3), (7), (1);
select * from ( (select * from t1 limit 2) order by 1 desc) as dt;
a
7
3
(values (3), (7), (1) limit 2) order by 1 desc;
3
7
3
select * from ( (values (3), (7), (1) limit 2) order by 1 desc) as dt;
3
7
3
select * from ( select * from t1 order by 1 limit 2 ) as dt;
a
1
3
values (3),(7),(1) order by 1 limit 2;
3
1
3
select * from ( values (3),(7),(1) order by 1 limit 2 ) as dt;
3
1
3
values (3),(7),(1) union values (2),(4) order by 1 limit 2;
3
1
2
select * from (values (3),(7),(1) union values (2),(4) order by 1 limit 2) as dt;
3
1
2
drop table t1;
End of 10.3 tests
......@@ -1628,4 +1628,26 @@ select * from t1;
drop table t1;
--echo #
--echo # MDEV-25484: Derived table using TVC with LIMIT and ORDER BY
--echo #
create table t1 (a int);
insert into t1 values (3), (7), (1);
select * from ( (select * from t1 limit 2) order by 1 desc) as dt;
(values (3), (7), (1) limit 2) order by 1 desc;
select * from ( (values (3), (7), (1) limit 2) order by 1 desc) as dt;
select * from ( select * from t1 order by 1 limit 2 ) as dt;
values (3),(7),(1) order by 1 limit 2;
select * from ( values (3),(7),(1) order by 1 limit 2 ) as dt;
values (3),(7),(1) union values (2),(4) order by 1 limit 2;
select * from (values (3),(7),(1) union values (2),(4) order by 1 limit 2) as dt;
drop table t1;
--echo End of 10.3 tests
......@@ -8396,8 +8396,15 @@ bool LEX::tvc_finalize_derived()
thd->parse_error();
return true;
}
if (unlikely(!(current_select->tvc=
new (thd->mem_root)
table_value_constr(many_values,
current_select,
current_select->options))))
return true;
restore_values_list_state();
current_select->linkage= DERIVED_TABLE_TYPE;
return tvc_finalize();
return false;
}
......
......@@ -12855,10 +12855,13 @@ order_clause:
created yet.
*/
SELECT_LEX *first_sl= unit->first_select();
if (unlikely(!unit->is_unit_op() &&
(first_sl->order_list.elements ||
first_sl->select_limit) &&
if (unlikely(!first_sl->next_select() && first_sl->tvc &&
unit->add_fake_select_lex(thd)))
MYSQL_YYABORT;
else if (unlikely(!unit->is_unit_op() &&
(first_sl->order_list.elements ||
first_sl->select_limit) &&
unit->add_fake_select_lex(thd)))
MYSQL_YYABORT;
}
if (sel->master_unit()->is_unit_op() && !sel->braces)
......@@ -12907,7 +12910,8 @@ limit_clause_init:
LIMIT
{
SELECT_LEX *sel= Select;
if (sel->master_unit()->is_unit_op() && !sel->braces)
if (sel->master_unit()->is_unit_op() && !sel->braces &&
sel->master_unit()->fake_select_lex)
{
/* Move LIMIT that belongs to UNION to fake_select_lex */
Lex->current_select= sel->master_unit()->fake_select_lex;
......
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