From ea187cfd4297e262328b7c376c920850cb23353d Mon Sep 17 00:00:00 2001 From: "bell@sanja.is.com.ua" <> Date: Sun, 14 Sep 2003 22:12:55 +0300 Subject: [PATCH] fixed proccesing global LIMIT in last SELECT of UNION --- mysql-test/r/subselect.result | 5 +++-- mysql-test/r/union.result | 4 ++-- mysql-test/t/subselect.test | 1 + sql/sql_parse.cc | 4 ++++ sql/sql_union.cc | 32 ++++++++++++++++++++++---------- 5 files changed, 32 insertions(+), 14 deletions(-) diff --git a/mysql-test/r/subselect.result b/mysql-test/r/subselect.result index 6cac5a9bc6c..703360dc7b5 100644 --- a/mysql-test/r/subselect.result +++ b/mysql-test/r/subselect.result @@ -1046,8 +1046,9 @@ t1 CREATE TABLE `t1` ( ) TYPE=MyISAM CHARSET=latin1 drop table t1; CREATE TABLE t1 SELECT (SELECT 1 as a UNION SELECT 1+1 limit 1,1) as a; -Warnings: -Warning 1262 Data truncated, NULL supplied to NOT NULL column 'a' at row 1 +select * from t1; +a +2 SHOW CREATE TABLE t1; Table Create Table t1 CREATE TABLE `t1` ( diff --git a/mysql-test/r/union.result b/mysql-test/r/union.result index 2e962190762..952ed566132 100644 --- a/mysql-test/r/union.result +++ b/mysql-test/r/union.result @@ -409,7 +409,7 @@ found_rows() SELECT SQL_CALC_FOUND_ROWS * FROM t1 UNION SELECT * FROM t2 LIMIT 2,2; a 3 -5 +4 select found_rows(); found_rows() 6 @@ -423,7 +423,7 @@ found_rows() 5 SELECT * FROM t1 UNION SELECT * FROM t2 ORDER BY a desc LIMIT 1; a -3 +5 (SELECT * FROM t1 ORDER by a) UNION ALL (SELECT * FROM t2 ORDER BY a) ORDER BY A desc LIMIT 4; a 5 diff --git a/mysql-test/t/subselect.test b/mysql-test/t/subselect.test index ef46ba7d12c..c6a574bae62 100644 --- a/mysql-test/t/subselect.test +++ b/mysql-test/t/subselect.test @@ -606,6 +606,7 @@ CREATE TABLE t1 SELECT * FROM (SELECT 1 as a,(SELECT a+0)) a; SHOW CREATE TABLE t1; drop table t1; CREATE TABLE t1 SELECT (SELECT 1 as a UNION SELECT 1+1 limit 1,1) as a; +select * from t1; SHOW CREATE TABLE t1; drop table t1; diff --git a/sql/sql_parse.cc b/sql/sql_parse.cc index d987a4ba8f1..2f770e329a1 100644 --- a/sql/sql_parse.cc +++ b/sql/sql_parse.cc @@ -1723,6 +1723,10 @@ mysql_execute_command(THD *thd) break; // Error message is given } + /* + In case of single SELECT unit->global_parameters points on first SELECT + TODO: move counters to SELECT_LEX + */ unit->offset_limit_cnt= (ha_rows) unit->global_parameters->offset_limit; unit->select_limit_cnt= (ha_rows) (unit->global_parameters->select_limit+ unit->global_parameters->offset_limit); diff --git a/sql/sql_union.cc b/sql/sql_union.cc index 2d7bee54da8..ae596625bf7 100644 --- a/sql/sql_union.cc +++ b/sql/sql_union.cc @@ -262,8 +262,23 @@ int st_select_lex_unit::exec() res= sl->join->reinit(); else { - offset_limit_cnt= sl->offset_limit; - select_limit_cnt= sl->select_limit+sl->offset_limit; + if (sl != global_parameters) + { + offset_limit_cnt= sl->offset_limit; + select_limit_cnt= sl->select_limit+sl->offset_limit; + } + else + { + offset_limit_cnt= 0; + /* + We can't use LIMIT at this stage if we are using ORDER BY for the + whole query + */ + if (sl->order_list.first) + select_limit_cnt= HA_POS_ERROR; + else + select_limit_cnt= sl->select_limit+sl->offset_limit; + } if (select_limit_cnt < sl->select_limit) select_limit_cnt= HA_POS_ERROR; // no limit @@ -352,14 +367,11 @@ int st_select_lex_unit::exec() { ulong options= thd->options; thd->lex.current_select= fake_select_lex; - if (select_cursor->braces) - { - offset_limit_cnt= global_parameters->offset_limit; - select_limit_cnt= global_parameters->select_limit + - global_parameters->offset_limit; - if (select_limit_cnt < global_parameters->select_limit) - select_limit_cnt= HA_POS_ERROR; // no limit - } + offset_limit_cnt= global_parameters->offset_limit; + select_limit_cnt= global_parameters->select_limit + + global_parameters->offset_limit; + if (select_limit_cnt < global_parameters->select_limit) + select_limit_cnt= HA_POS_ERROR; // no limit if (select_limit_cnt == HA_POS_ERROR) options&= ~OPTION_FOUND_ROWS; else if (found_rows_for_union && !describe)