Skip to content
Projects
Groups
Snippets
Help
Loading...
Help
Support
Keyboard shortcuts
?
Submit feedback
Contribute to GitLab
Sign in / Register
Toggle navigation
M
MariaDB
Project overview
Project overview
Details
Activity
Releases
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Issues
0
Issues
0
List
Boards
Labels
Milestones
Merge Requests
0
Merge Requests
0
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Analytics
Analytics
CI / CD
Repository
Value Stream
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
nexedi
MariaDB
Commits
ead6f225
Commit
ead6f225
authored
May 08, 2002
by
bell@sanja.is.com.ua
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
new SELECT_LEX structures used for storing global ORDER BY, global LIMIT & limit counters
parent
494184ff
Changes
15
Expand all
Hide whitespace changes
Inline
Side-by-side
Showing
15 changed files
with
208 additions
and
181 deletions
+208
-181
mysql-test/r/union.result
mysql-test/r/union.result
+0
-1
sql/item_sum.cc
sql/item_sum.cc
+5
-3
sql/mysql_priv.h
sql/mysql_priv.h
+2
-1
sql/sql_class.cc
sql/sql_class.cc
+11
-8
sql/sql_class.h
sql/sql_class.h
+14
-9
sql/sql_delete.cc
sql/sql_delete.cc
+2
-1
sql/sql_derived.cc
sql/sql_derived.cc
+13
-11
sql/sql_insert.cc
sql/sql_insert.cc
+8
-6
sql/sql_lex.cc
sql/sql_lex.cc
+4
-2
sql/sql_parse.cc
sql/sql_parse.cc
+30
-25
sql/sql_select.cc
sql/sql_select.cc
+50
-43
sql/sql_select.h
sql/sql_select.h
+4
-1
sql/sql_union.cc
sql/sql_union.cc
+40
-62
sql/sql_update.cc
sql/sql_update.cc
+9
-4
sql/sql_yacc.yy
sql/sql_yacc.yy
+16
-4
No files found.
mysql-test/r/union.result
View file @
ead6f225
...
...
@@ -88,7 +88,6 @@ explain (select a,b from t1 limit 2) union all (select a,b from t2 order by a l
table type possible_keys key key_len ref rows Extra
t1 ALL NULL NULL NULL NULL 4
t2 ALL NULL NULL NULL NULL 4 Using filesort
t1 ALL NULL NULL NULL NULL 4
(select sql_calc_found_rows a,b from t1 limit 2) union all (select a,b from t2 order by a) limit 2;
a b
1 a
...
...
sql/item_sum.cc
View file @
ead6f225
...
...
@@ -940,6 +940,7 @@ bool Item_sum_count_distinct::fix_fields(THD *thd,TABLE_LIST *tables)
bool
Item_sum_count_distinct
::
setup
(
THD
*
thd
)
{
List
<
Item
>
list
;
SELECT_LEX
*
select_lex
=
current_lex
->
select
;
/* Create a table with an unique key over all parameters */
for
(
uint
i
=
0
;
i
<
arg_count
;
i
++
)
{
...
...
@@ -961,9 +962,10 @@ bool Item_sum_count_distinct::setup(THD *thd)
free_tmp_table
(
thd
,
table
);
tmp_table_param
->
cleanup
();
}
if
(
!
(
table
=
create_tmp_table
(
thd
,
tmp_table_param
,
list
,
(
ORDER
*
)
0
,
1
,
0
,
0
,
current_lex
->
select
->
options
|
thd
->
options
)))
if
(
!
(
table
=
create_tmp_table
(
thd
,
tmp_table_param
,
list
,
(
ORDER
*
)
0
,
1
,
0
,
0
,
select_lex
->
options
|
thd
->
options
,
(
SELECT_LEX_UNIT
*
)
select_lex
->
master
)))
return
1
;
table
->
file
->
extra
(
HA_EXTRA_NO_ROWS
);
// Don't update rows
table
->
no_rows
=
1
;
...
...
sql/mysql_priv.h
View file @
ead6f225
...
...
@@ -359,7 +359,8 @@ int setup_order(THD *thd,TABLE_LIST *tables, List<Item> &fields,
int
handle_select
(
THD
*
thd
,
LEX
*
lex
,
select_result
*
result
);
int
mysql_select
(
THD
*
thd
,
TABLE_LIST
*
tables
,
List
<
Item
>
&
list
,
COND
*
conds
,
ORDER
*
order
,
ORDER
*
group
,
Item
*
having
,
ORDER
*
proc_param
,
ulong
select_type
,
select_result
*
result
);
ulong
select_type
,
select_result
*
result
,
SELECT_LEX_UNIT
*
unit
);
int
mysql_union
(
THD
*
thd
,
LEX
*
lex
,
select_result
*
result
);
int
mysql_derived
(
THD
*
thd
,
LEX
*
lex
,
SELECT_LEX_UNIT
*
s
,
TABLE_LIST
*
t
);
Field
*
create_tmp_field
(
THD
*
thd
,
TABLE
*
table
,
Item
*
item
,
Item
::
Type
type
,
...
...
sql/sql_class.cc
View file @
ead6f225
...
...
@@ -389,9 +389,9 @@ bool select_send::send_data(List<Item> &items)
String
*
packet
=
&
thd
->
packet
;
DBUG_ENTER
(
"send_data"
);
if
(
thd
->
offset_limi
t
)
if
(
unit
->
offset_limit_cn
t
)
{
// using limit offset,count
thd
->
offset_limi
t
--
;
unit
->
offset_limit_cn
t
--
;
DBUG_RETURN
(
0
);
}
packet
->
length
(
0
);
// Reset packet
...
...
@@ -439,11 +439,12 @@ select_export::~select_export()
}
int
select_export
::
prepare
(
List
<
Item
>
&
list
)
select_export
::
prepare
(
List
<
Item
>
&
list
,
SELECT_LEX_UNIT
*
u
)
{
char
path
[
FN_REFLEN
];
uint
option
=
4
;
bool
blob_flag
=
0
;
unit
=
u
;
#ifdef DONT_ALLOW_FULL_LOAD_DATA_PATHS
option
|=
1
;
// Force use of db directory
#endif
...
...
@@ -510,9 +511,9 @@ bool select_export::send_data(List<Item> &items)
String
tmp
(
buff
,
sizeof
(
buff
)),
*
res
;
tmp
.
length
(
0
);
if
(
thd
->
offset_limi
t
)
if
(
unit
->
offset_limit_cn
t
)
{
// using limit offset,count
thd
->
offset_limi
t
--
;
unit
->
offset_limit_cn
t
--
;
DBUG_RETURN
(
0
);
}
row_count
++
;
...
...
@@ -678,9 +679,11 @@ select_dump::~select_dump()
}
int
select_dump
::
prepare
(
List
<
Item
>
&
list
__attribute__
((
unused
)))
select_dump
::
prepare
(
List
<
Item
>
&
list
__attribute__
((
unused
)),
SELECT_LEX_UNIT
*
u
)
{
uint
option
=
4
;
unit
=
u
;
#ifdef DONT_ALLOW_FULL_LOAD_DATA_PATHS
option
|=
1
;
// Force use of db directory
#endif
...
...
@@ -719,9 +722,9 @@ bool select_dump::send_data(List<Item> &items)
Item
*
item
;
DBUG_ENTER
(
"send_data"
);
if
(
thd
->
offset_limi
t
)
if
(
unit
->
offset_limit_cn
t
)
{
// using limit offset,count
thd
->
offset_limi
t
--
;
unit
->
offset_limit_cn
t
--
;
DBUG_RETURN
(
0
);
}
if
(
row_count
++
>
1
)
...
...
sql/sql_class.h
View file @
ead6f225
...
...
@@ -382,7 +382,7 @@ class THD :public ilink {
#endif
ulonglong
next_insert_id
,
last_insert_id
,
current_insert_id
,
limit_found_rows
;
ha_rows
select_limit
,
offset_limit
,
default_select_limit
,
cuted_fields
,
ha_rows
default_select_limit
,
cuted_fields
,
max_join_size
,
sent_row_count
,
examined_row_count
;
table_map
used_tables
;
UC
*
user_connect
;
...
...
@@ -551,10 +551,15 @@ void send_error(NET *net,uint sql_errno=0, const char *err=0);
class
select_result
:
public
Sql_alloc
{
protected:
THD
*
thd
;
SELECT_LEX_UNIT
*
unit
;
public:
select_result
();
virtual
~
select_result
()
{};
virtual
int
prepare
(
List
<
Item
>
&
list
)
{
return
0
;
}
virtual
int
prepare
(
List
<
Item
>
&
list
,
SELECT_LEX_UNIT
*
u
)
{
unit
=
u
;
return
0
;
}
virtual
bool
send_fields
(
List
<
Item
>
&
list
,
uint
flag
)
=
0
;
virtual
bool
send_data
(
List
<
Item
>
&
items
)
=
0
;
virtual
void
initialize_tables
(
JOIN
*
join
=
0
)
{}
...
...
@@ -587,7 +592,7 @@ class select_export :public select_result {
public:
select_export
(
sql_exchange
*
ex
)
:
exchange
(
ex
),
file
(
-
1
),
row_count
(
0L
)
{}
~
select_export
();
int
prepare
(
List
<
Item
>
&
list
);
int
prepare
(
List
<
Item
>
&
list
,
SELECT_LEX_UNIT
*
u
);
bool
send_fields
(
List
<
Item
>
&
list
,
uint
flag
)
{
return
0
;
}
bool
send_data
(
List
<
Item
>
&
items
);
...
...
@@ -606,7 +611,7 @@ class select_dump :public select_result {
select_dump
(
sql_exchange
*
ex
)
:
exchange
(
ex
),
file
(
-
1
),
row_count
(
0L
)
{
path
[
0
]
=
0
;
}
~
select_dump
();
int
prepare
(
List
<
Item
>
&
list
);
int
prepare
(
List
<
Item
>
&
list
,
SELECT_LEX_UNIT
*
u
);
bool
send_fields
(
List
<
Item
>
&
list
,
uint
flag
)
{
return
0
;
}
bool
send_data
(
List
<
Item
>
&
items
);
...
...
@@ -629,7 +634,7 @@ class select_insert :public select_result {
info
.
handle_duplicates
=
duplic
;
}
~
select_insert
();
int
prepare
(
List
<
Item
>
&
list
);
int
prepare
(
List
<
Item
>
&
list
,
SELECT_LEX_UNIT
*
u
);
bool
send_fields
(
List
<
Item
>
&
list
,
uint
flag
)
{
return
0
;
}
bool
send_data
(
List
<
Item
>
&
items
);
...
...
@@ -658,7 +663,7 @@ class select_create: public select_insert {
create_info
(
create_info_par
),
lock
(
0
)
{}
int
prepare
(
List
<
Item
>
&
list
);
int
prepare
(
List
<
Item
>
&
list
,
SELECT_LEX_UNIT
*
u
);
bool
send_data
(
List
<
Item
>
&
values
);
bool
send_eof
();
void
abort
();
...
...
@@ -672,7 +677,7 @@ class select_union :public select_result {
select_union
(
TABLE
*
table_par
);
~
select_union
();
int
prepare
(
List
<
Item
>
&
list
);
int
prepare
(
List
<
Item
>
&
list
,
SELECT_LEX_UNIT
*
u
);
bool
send_fields
(
List
<
Item
>
&
list
,
uint
flag
)
{
return
0
;
}
bool
send_data
(
List
<
Item
>
&
items
);
...
...
@@ -787,7 +792,7 @@ class Unique :public Sql_alloc
multi_delete
(
THD
*
thd
,
TABLE_LIST
*
dt
,
thr_lock_type
lock_option_arg
,
uint
num_of_tables
);
~
multi_delete
();
int
prepare
(
List
<
Item
>
&
list
);
int
prepare
(
List
<
Item
>
&
list
,
SELECT_LEX_UNIT
*
u
);
bool
send_fields
(
List
<
Item
>
&
list
,
uint
flag
)
{
return
0
;
}
bool
send_data
(
List
<
Item
>
&
items
);
...
...
@@ -816,7 +821,7 @@ class Unique :public Sql_alloc
enum
enum_duplicates
handle_duplicates
,
thr_lock_type
lock_option_arg
,
uint
num
);
~
multi_update
();
int
prepare
(
List
<
Item
>
&
list
);
int
prepare
(
List
<
Item
>
&
list
,
SELECT_LEX_UNIT
*
u
);
bool
send_fields
(
List
<
Item
>
&
list
,
uint
flag
)
{
return
0
;
}
bool
send_data
(
List
<
Item
>
&
items
);
...
...
sql/sql_delete.cc
View file @
ead6f225
...
...
@@ -232,9 +232,10 @@ multi_delete::multi_delete(THD *thd_arg, TABLE_LIST *dt,
int
multi_delete
::
prepare
(
List
<
Item
>
&
values
)
multi_delete
::
prepare
(
List
<
Item
>
&
values
,
SELECT_LEX_UNIT
*
u
)
{
DBUG_ENTER
(
"multi_delete::prepare"
);
unit
=
u
;
do_delete
=
true
;
thd
->
proc_info
=
"deleting from main table"
;
...
...
sql/sql_derived.cc
View file @
ead6f225
...
...
@@ -28,13 +28,13 @@
static
const
char
*
any_db
=
"*any*"
;
// Special symbol for check_access
int
mysql_derived
(
THD
*
thd
,
LEX
*
lex
,
SELECT_LEX_UNIT
*
s
,
TABLE_LIST
*
t
)
int
mysql_derived
(
THD
*
thd
,
LEX
*
lex
,
SELECT_LEX_UNIT
*
unit
,
TABLE_LIST
*
t
)
{
/*
TODO: make derived tables with union inside (now only 1 SELECT may be
procesed)
*/
SELECT_LEX
*
sl
=
(
SELECT_LEX
*
)
s
->
slave
;
SELECT_LEX
*
sl
=
(
SELECT_LEX
*
)
unit
->
slave
;
List
<
Item
>
item_list
;
TABLE
*
table
;
int
res
;
...
...
@@ -75,9 +75,11 @@ int mysql_derived(THD *thd, LEX *lex, SELECT_LEX_UNIT *s, TABLE_LIST *t)
}
bzero
((
char
*
)
&
tmp_table_param
,
sizeof
(
tmp_table_param
));
tmp_table_param
.
field_count
=
item_list
.
elements
;
if
(
!
(
table
=
create_tmp_table
(
thd
,
&
tmp_table_param
,
sl
->
item_list
,
(
ORDER
*
)
0
,
0
,
1
,
0
,
(
sl
->
options
|
thd
->
options
|
TMP_TABLE_ALL_COLUMNS
))))
if
(
!
(
table
=
create_tmp_table
(
thd
,
&
tmp_table_param
,
sl
->
item_list
,
(
ORDER
*
)
0
,
0
,
1
,
0
,
(
sl
->
options
|
thd
->
options
|
TMP_TABLE_ALL_COLUMNS
),
unit
)))
{
res
=-
1
;
goto
exit
;
...
...
@@ -85,11 +87,11 @@ int mysql_derived(THD *thd, LEX *lex, SELECT_LEX_UNIT *s, TABLE_LIST *t)
if
((
derived_result
=
new
select_union
(
table
)))
{
thd
->
offset_limit
=
sl
->
offset_limit
;
thd
->
select_limit
=
sl
->
select_limit
+
sl
->
offset_limit
;
if
(
thd
->
select_limi
t
<
sl
->
select_limit
)
thd
->
select_limi
t
=
HA_POS_ERROR
;
if
(
thd
->
select_limi
t
==
HA_POS_ERROR
)
unit
->
offset_limit_cnt
=
sl
->
offset_limit
;
unit
->
select_limit_cnt
=
sl
->
select_limit
+
sl
->
offset_limit
;
if
(
unit
->
select_limit_cn
t
<
sl
->
select_limit
)
unit
->
select_limit_cn
t
=
HA_POS_ERROR
;
if
(
unit
->
select_limit_cn
t
==
HA_POS_ERROR
)
sl
->
options
&=
~
OPTION_FOUND_ROWS
;
res
=
mysql_select
(
thd
,
tables
,
sl
->
item_list
,
...
...
@@ -97,7 +99,7 @@ int mysql_derived(THD *thd, LEX *lex, SELECT_LEX_UNIT *s, TABLE_LIST *t)
(
ORDER
*
)
sl
->
group_list
.
first
,
sl
->
having
,
(
ORDER
*
)
NULL
,
sl
->
options
|
thd
->
options
|
SELECT_NO_UNLOCK
,
derived_result
);
derived_result
,
unit
);
if
(
!
res
)
{
// Here we entirely fix both TABLE_LIST and list of SELECT's as there were no derived tables
...
...
sql/sql_insert.cc
View file @
ead6f225
...
...
@@ -1266,10 +1266,11 @@ bool delayed_insert::handle_inserts(void)
***************************************************************************/
int
select_insert
::
prepare
(
List
<
Item
>
&
values
)
select_insert
::
prepare
(
List
<
Item
>
&
values
,
SELECT_LEX_UNIT
*
u
)
{
DBUG_ENTER
(
"select_insert::prepare"
);
unit
=
u
;
save_time_stamp
=
table
->
time_stamp
;
if
(
check_insert_fields
(
thd
,
table
,
*
fields
,
values
,
1
))
DBUG_RETURN
(
1
);
...
...
@@ -1302,9 +1303,9 @@ select_insert::~select_insert()
bool
select_insert
::
send_data
(
List
<
Item
>
&
values
)
{
if
(
thd
->
offset_limi
t
)
if
(
unit
->
offset_limit_cn
t
)
{
// using limit offset,count
thd
->
offset_limi
t
--
;
unit
->
offset_limit_cn
t
--
;
return
0
;
}
if
(
fields
->
elements
)
...
...
@@ -1380,10 +1381,11 @@ bool select_insert::send_eof()
***************************************************************************/
int
select_create
::
prepare
(
List
<
Item
>
&
values
)
select_create
::
prepare
(
List
<
Item
>
&
values
,
SELECT_LEX_UNIT
*
u
)
{
DBUG_ENTER
(
"select_create::prepare"
);
unit
=
u
;
table
=
create_table_from_items
(
thd
,
create_info
,
db
,
name
,
extra_fields
,
keys
,
&
values
,
&
lock
);
if
(
!
table
)
...
...
@@ -1413,9 +1415,9 @@ select_create::prepare(List<Item> &values)
bool
select_create
::
send_data
(
List
<
Item
>
&
values
)
{
if
(
thd
->
offset_limi
t
)
if
(
unit
->
offset_limit_cn
t
)
{
// using limit offset,count
thd
->
offset_limi
t
--
;
unit
->
offset_limit_cn
t
--
;
return
0
;
}
fill_record
(
field
,
values
);
...
...
sql/sql_lex.cc
View file @
ead6f225
...
...
@@ -895,14 +895,16 @@ void st_select_lex_node::init_select()
order_list
.
elements
=
0
;
order_list
.
first
=
0
;
order_list
.
next
=
(
byte
**
)
&
order_list
.
first
;
select_limit
=
offset_limit
=
0
;
select_limit
=
HA_POS_ERROR
;
offset_limit
=
0
;
}
void
st_select_lex_unit
::
init_query
()
{
st_select_lex_node
::
init_query
();
global_parameters
=
this
;
select_limit_cnt
=
offset_limit_cnt
=
0
;
select_limit_cnt
=
HA_POS_ERROR
;
offset_limit_cnt
=
0
;
}
void
st_select_lex
::
init_query
()
...
...
sql/sql_parse.cc
View file @
ead6f225
...
...
@@ -1203,11 +1203,12 @@ bool dispatch_command(enum enum_server_command command, THD *thd,
void
mysql_execute_command
(
void
)
{
int
res
=
0
;
THD
*
thd
=
current_thd
;
int
res
=
0
;
THD
*
thd
=
current_thd
;
LEX
*
lex
=
&
thd
->
lex
;
TABLE_LIST
*
tables
=
(
TABLE_LIST
*
)
lex
->
select_lex
.
table_list
.
first
;
SELECT_LEX
*
select_lex
=
lex
->
select
;
TABLE_LIST
*
tables
=
(
TABLE_LIST
*
)
lex
->
select_lex
.
table_list
.
first
;
SELECT_LEX
*
select_lex
=
lex
->
select
;
SELECT_LEX_UNIT
*
unit
=
&
lex
->
unit
;
DBUG_ENTER
(
"mysql_execute_command"
);
if
(
thd
->
slave_thread
)
...
...
@@ -1274,11 +1275,11 @@ mysql_execute_command(void)
break
;
// Error message is given
}
thd
->
offset_limit
=
select_lex
->
offset_limit
;
thd
->
select_limit
=
select_lex
->
select_limit
+
select_lex
->
offset_limit
;
if
(
thd
->
select_limi
t
<
select_lex
->
select_limit
)
thd
->
select_limi
t
=
HA_POS_ERROR
;
// no limit
if
(
thd
->
select_limi
t
==
HA_POS_ERROR
)
unit
->
offset_limit_cnt
=
select_lex
->
offset_limit
;
unit
->
select_limit_cnt
=
select_lex
->
select_limit
+
select_lex
->
offset_limit
;
if
(
unit
->
select_limit_cn
t
<
select_lex
->
select_limit
)
unit
->
select_limit_cn
t
=
HA_POS_ERROR
;
// no limit
if
(
unit
->
select_limit_cn
t
==
HA_POS_ERROR
)
select_lex
->
options
&=
~
OPTION_FOUND_ROWS
;
if
(
lex
->
exchange
)
...
...
@@ -1503,10 +1504,11 @@ mysql_execute_command(void)
for
(
table
=
tables
->
next
;
table
;
table
=
table
->
next
)
table
->
lock_type
=
lex
->
lock_option
;
}
thd
->
offset_limit
=
select_lex
->
offset_limit
;
thd
->
select_limit
=
select_lex
->
select_limit
+
select_lex
->
offset_limit
;
if
(
thd
->
select_limit
<
select_lex
->
select_limit
)
thd
->
select_limit
=
HA_POS_ERROR
;
// No limit
unit
->
offset_limit_cnt
=
select_lex
->
offset_limit
;
unit
->
select_limit_cnt
=
select_lex
->
select_limit
+
select_lex
->
offset_limit
;
if
(
unit
->
select_limit_cnt
<
select_lex
->
select_limit
)
unit
->
select_limit_cnt
=
HA_POS_ERROR
;
// No limit
/* Skip first table, which is the table we are creating */
lex
->
select_lex
.
table_list
.
first
=
...
...
@@ -1788,13 +1790,13 @@ mysql_execute_command(void)
while
((
item
=
value_list
++
))
total_list
.
push_back
(
item
);
res
=
mysql_select
(
thd
,
tables
,
total_list
,
select_lex
->
where
,
(
ORDER
*
)
NULL
,(
ORDER
*
)
NULL
,
(
Item
*
)
NULL
,
(
ORDER
*
)
NULL
,
select_lex
->
options
|
thd
->
options
|
SELECT_NO_JOIN_CACHE
,
resul
t
);
res
=
mysql_select
(
thd
,
tables
,
total_list
,
select_lex
->
where
,
(
ORDER
*
)
NULL
,
(
ORDER
*
)
NULL
,
(
Item
*
)
NULL
,
(
ORDER
*
)
NULL
,
select_lex
->
options
|
thd
->
options
|
SELECT_NO_JOIN_CACHE
,
result
,
uni
t
);
delete
result
;
}
else
...
...
@@ -1844,10 +1846,10 @@ mysql_execute_command(void)
}
select_result
*
result
;
thd
->
offset_limit
=
select_lex
->
offset_limit
;
thd
->
select_limit
=
select_lex
->
select_limit
+
select_lex
->
offset_limit
;
if
(
thd
->
select_limi
t
<
select_lex
->
select_limit
)
thd
->
select_limi
t
=
HA_POS_ERROR
;
// No limit
unit
->
offset_limit_cnt
=
select_lex
->
offset_limit
;
unit
->
select_limit_cnt
=
select_lex
->
select_limit
+
select_lex
->
offset_limit
;
if
(
unit
->
select_limit_cn
t
<
select_lex
->
select_limit
)
unit
->
select_limit_cn
t
=
HA_POS_ERROR
;
// No limit
if
(
check_dup
(
tables
->
db
,
tables
->
real_name
,
tables
->
next
))
{
...
...
@@ -1963,7 +1965,7 @@ mysql_execute_command(void)
(
ORDER
*
)
NULL
,
select_lex
->
options
|
thd
->
options
|
SELECT_NO_JOIN_CACHE
,
result
);
result
,
unit
);
delete
result
;
}
else
...
...
@@ -2667,8 +2669,10 @@ mysql_init_query(THD *thd)
{
DBUG_ENTER
(
"mysql_init_query"
);
thd
->
lex
.
unit
.
init_query
();
thd
->
lex
.
unit
.
init_select
();
thd
->
lex
.
select_lex
.
init_query
();
thd
->
lex
.
unit
.
slave
=
&
thd
->
lex
.
select_lex
;
thd
->
lex
.
unit
.
select_limit
=
thd
->
default_select_limit
;
//Global limit
thd
->
lex
.
select_lex
.
master
=
&
thd
->
lex
.
unit
;
thd
->
lex
.
select_lex
.
prev
=
&
thd
->
lex
.
unit
.
slave
;
thd
->
lex
.
value_list
.
empty
();
...
...
@@ -2716,6 +2720,7 @@ mysql_new_select(LEX *lex, bool move_down)
else
select_lex
->
include_neighbour
(
lex
->
select
);
((
SELECT_LEX_UNIT
*
)
select_lex
->
master
)
->
global_parameters
=
select_lex
;
select_lex
->
include_global
(
&
lex
->
select
->
link_next
);
lex
->
select
=
select_lex
;
return
0
;
...
...
sql/sql_select.cc
View file @
ead6f225
This diff is collapsed.
Click to expand it.
sql/sql_select.h
View file @
ead6f225
...
...
@@ -173,6 +173,8 @@ class JOIN {
select_result
*
result
;
TMP_TABLE_PARAM
tmp_table_param
;
MYSQL_LOCK
*
lock
;
// unit structure (with global parameters) for this select
SELECT_LEX_UNIT
*
unit
;
};
...
...
@@ -187,7 +189,8 @@ void TEST_join(JOIN *join);
bool
store_val_in_field
(
Field
*
field
,
Item
*
val
);
TABLE
*
create_tmp_table
(
THD
*
thd
,
TMP_TABLE_PARAM
*
param
,
List
<
Item
>
&
fields
,
ORDER
*
group
,
bool
distinct
,
bool
save_sum_fields
,
bool
allow_distinct_limit
,
ulong
select_options
);
bool
allow_distinct_limit
,
ulong
select_options
,
SELECT_LEX_UNIT
*
unit
);
void
free_tmp_table
(
THD
*
thd
,
TABLE
*
entry
);
void
count_field_types
(
TMP_TABLE_PARAM
*
param
,
List
<
Item
>
&
fields
,
bool
reset_with_sum_func
);
...
...
sql/sql_union.cc
View file @
ead6f225
...
...
@@ -27,8 +27,8 @@
int
mysql_union
(
THD
*
thd
,
LEX
*
lex
,
select_result
*
result
)
{
SELECT_LEX
*
sl
,
*
last_sl
,
*
lex_sl
;
ORDER
*
order
;
SELECT_LEX
*
sl
;
SELECT_LEX_UNIT
*
unit
=
&
(
lex
->
unit
)
;
List
<
Item
>
item_list
;
TABLE
*
table
;
int
describe
=
(
lex
->
select_lex
.
options
&
SELECT_DESCRIBE
)
?
1
:
0
;
...
...
@@ -39,12 +39,12 @@ int mysql_union(THD *thd, LEX *lex,select_result *result)
TMP_TABLE_PARAM
tmp_table_param
;
select_union
*
union_result
;
DBUG_ENTER
(
"mysql_union"
);
st_select_lex_node
*
global
;
/* Fix tables 'to-be-unioned-from' list to point at opened tables */
last_sl
=
&
lex
->
select_lex
;
for
(
sl
=
last_sl
;
sl
&&
sl
->
linkage
!=
GLOBAL_OPTIONS_TYPE
;
last_sl
=
sl
,
sl
=
(
SELECT_LEX
*
)
sl
->
next
)
for
(
sl
=
&
lex
->
select_lex
;
sl
;
sl
=
(
SELECT_LEX
*
)
sl
->
next
)
{
for
(
TABLE_LIST
*
cursor
=
(
TABLE_LIST
*
)
sl
->
table_list
.
first
;
cursor
;
...
...
@@ -52,31 +52,13 @@ int mysql_union(THD *thd, LEX *lex,select_result *result)
cursor
->
table
=
((
TABLE_LIST
*
)
cursor
->
table
)
->
table
;
}
/*
last_sel now points at the last select where the ORDER BY is stored
*/
if
(
sl
)
/*
Global option
*/
if
(
((
void
*
)(
global
=
unit
->
global_parameters
))
==
((
void
*
)
unit
)
)
{
/*
The found SL is an extra SELECT_LEX argument that contains
the ORDER BY and LIMIT parameter for the whole UNION
*/
lex_sl
=
sl
;
order
=
(
ORDER
*
)
lex_sl
->
order_list
.
first
;
found_rows_for_union
=
lex
->
select_lex
.
options
&
OPTION_FOUND_ROWS
&&
!
describe
&&
sl
->
select_limit
;
found_rows_for_union
=
lex
->
select_lex
.
options
&
OPTION_FOUND_ROWS
&&
!
describe
&&
global
->
select_limit
;
if
(
found_rows_for_union
)
lex
->
select_lex
.
options
^=
OPTION_FOUND_ROWS
;
// This is done to eliminate unnecessary slowing down of the first query
if
(
!
order
||
!
describe
)
last_sl
->
next
=
0
;
// Remove this extra element
}
else
if
(
!
last_sl
->
braces
)
{
lex_sl
=
last_sl
;
// ORDER BY is here
order
=
(
ORDER
*
)
lex_sl
->
order_list
.
first
;
}
else
{
lex_sl
=
0
;
order
=
0
;
}
if
(
describe
)
...
...
@@ -113,11 +95,12 @@ int mysql_union(THD *thd, LEX *lex,select_result *result)
bzero
((
char
*
)
&
tmp_table_param
,
sizeof
(
tmp_table_param
));
tmp_table_param
.
field_count
=
item_list
.
elements
;
if
(
!
(
table
=
create_tmp_table
(
thd
,
&
tmp_table_param
,
item_list
,
(
ORDER
*
)
0
,
!
describe
&
!
lex
->
union_option
,
1
,
0
,
(
lex
->
select_lex
.
options
|
thd
->
options
|
TMP_TABLE_ALL_COLUMNS
))))
if
(
!
(
table
=
create_tmp_table
(
thd
,
&
tmp_table_param
,
item_list
,
(
ORDER
*
)
0
,
!
describe
&
!
lex
->
union_option
,
1
,
0
,
(
lex
->
select_lex
.
options
|
thd
->
options
|
TMP_TABLE_ALL_COLUMNS
),
unit
)))
DBUG_RETURN
(
-
1
);
table
->
file
->
extra
(
HA_EXTRA_WRITE_CACHE
);
table
->
file
->
extra
(
HA_EXTRA_IGNORE_DUP_KEY
);
...
...
@@ -136,11 +119,11 @@ int mysql_union(THD *thd, LEX *lex,select_result *result)
for
(
sl
=
&
lex
->
select_lex
;
sl
;
sl
=
(
SELECT_LEX
*
)
sl
->
next
)
{
lex
->
select
=
sl
;
thd
->
offset_limit
=
sl
->
offset_limit
;
thd
->
select_limit
=
sl
->
select_limit
+
sl
->
offset_limit
;
if
(
thd
->
select_limi
t
<
sl
->
select_limit
)
thd
->
select_limi
t
=
HA_POS_ERROR
;
// no limit
if
(
thd
->
select_limi
t
==
HA_POS_ERROR
)
unit
->
offset_limit_cnt
=
sl
->
offset_limit
;
unit
->
select_limit_cnt
=
sl
->
select_limit
+
sl
->
offset_limit
;
if
(
unit
->
select_limit_cn
t
<
sl
->
select_limit
)
unit
->
select_limit_cn
t
=
HA_POS_ERROR
;
// no limit
if
(
unit
->
select_limit_cn
t
==
HA_POS_ERROR
)
sl
->
options
&=
~
OPTION_FOUND_ROWS
;
res
=
mysql_select
(
thd
,
...
...
@@ -155,7 +138,7 @@ int mysql_union(THD *thd, LEX *lex,select_result *result)
(
ORDER
*
)
NULL
,
sl
->
options
|
thd
->
options
|
SELECT_NO_UNLOCK
|
((
describe
)
?
SELECT_DESCRIBE
:
0
),
union_result
);
union_result
,
unit
);
if
(
res
)
goto
exit
;
}
...
...
@@ -187,26 +170,20 @@ int mysql_union(THD *thd, LEX *lex,select_result *result)
}
if
(
!
thd
->
fatal_error
)
// Check if EOM
{
if
(
lex_sl
)
{
thd
->
offset_limit
=
lex_sl
->
offset_limit
;
thd
->
select_limit
=
lex_sl
->
select_limit
+
lex_sl
->
offset_limit
;
if
(
thd
->
select_limit
<
lex_sl
->
select_limit
)
thd
->
select_limit
=
HA_POS_ERROR
;
// no limit
if
(
thd
->
select_limit
==
HA_POS_ERROR
)
thd
->
options
&=
~
OPTION_FOUND_ROWS
;
}
else
{
thd
->
offset_limit
=
0
;
thd
->
select_limit
=
thd
->
default_select_limit
;
}
st_select_lex_node
*
global
=
unit
->
global_parameters
;
unit
->
offset_limit_cnt
=
global
->
offset_limit
;
unit
->
select_limit_cnt
=
global
->
select_limit
+
global
->
offset_limit
;
if
(
unit
->
select_limit_cnt
<
global
->
select_limit
)
unit
->
select_limit_cnt
=
HA_POS_ERROR
;
// no limit
if
(
unit
->
select_limit_cnt
==
HA_POS_ERROR
)
thd
->
options
&=
~
OPTION_FOUND_ROWS
;
if
(
describe
)
thd
->
select_limit
=
HA_POS_ERROR
;
// no limit
res
=
mysql_select
(
thd
,
&
result_table_list
,
item_list
,
NULL
,
(
describe
)
?
0
:
order
,
(
ORDER
*
)
NULL
,
NULL
,
(
ORDER
*
)
NULL
,
thd
->
options
,
result
);
unit
->
select_limit_cnt
=
HA_POS_ERROR
;
// no limit
res
=
mysql_select
(
thd
,
&
result_table_list
,
item_list
,
NULL
,
(
describe
)
?
0
:
(
ORDER
*
)
global
->
order_list
.
first
,
(
ORDER
*
)
NULL
,
NULL
,
(
ORDER
*
)
NULL
,
thd
->
options
,
result
,
unit
);
if
(
found_rows_for_union
&&
!
res
)
thd
->
limit_found_rows
=
(
ulonglong
)
table
->
file
->
records
;
}
...
...
@@ -230,7 +207,7 @@ select_union::select_union(TABLE *table_par)
We can always use DUP_IGNORE because the temporary table will only
contain a unique key if we are using not using UNION ALL
*/
info
.
handle_duplicates
=
DUP_IGNORE
;
info
.
handle_duplicates
=
DUP_IGNORE
;
}
select_union
::~
select_union
()
...
...
@@ -238,8 +215,9 @@ select_union::~select_union()
}
int
select_union
::
prepare
(
List
<
Item
>
&
list
)
int
select_union
::
prepare
(
List
<
Item
>
&
list
,
SELECT_LEX_UNIT
*
u
)
{
unit
=
u
;
if
(
save_time_stamp
&&
list
.
elements
!=
table
->
fields
)
{
my_message
(
ER_WRONG_NUMBER_OF_COLUMNS_IN_SELECT
,
...
...
@@ -251,9 +229,9 @@ int select_union::prepare(List<Item> &list)
bool
select_union
::
send_data
(
List
<
Item
>
&
values
)
{
if
(
thd
->
offset_limi
t
)
if
(
unit
->
offset_limit_cn
t
)
{
// using limit offset,count
thd
->
offset_limi
t
--
;
unit
->
offset_limit_cn
t
--
;
return
0
;
}
fill_record
(
table
->
field
,
values
);
...
...
sql/sql_update.cc
View file @
ead6f225
...
...
@@ -379,9 +379,10 @@ multi_update::multi_update(THD *thd_arg, TABLE_LIST *ut, List<Item> &fs,
}
int
multi_update
::
prepare
(
List
<
Item
>
&
values
)
multi_update
::
prepare
(
List
<
Item
>
&
values
,
SELECT_LEX_UNIT
*
u
)
{
DBUG_ENTER
(
"multi_update::prepare"
);
unit
=
u
;
do_update
=
true
;
thd
->
count_cuted_fields
=
1
;
thd
->
cuted_fields
=
0L
;
...
...
@@ -466,15 +467,19 @@ multi_update::prepare(List<Item> &values)
}
if
(
counter
)
{
Field_string
offset
(
table_ref
->
table
->
file
->
ref_length
,
false
,
"offset"
,
table_ref
->
table
,
true
);
Field_string
offset
(
table_ref
->
table
->
file
->
ref_length
,
false
,
"offset"
,
table_ref
->
table
,
true
);
temp_fields
->
push_front
(
new
Item_field
(((
Field
*
)
&
offset
)));
// Here I make tmp tables
int
cnt
=
counter
-
1
;
TMP_TABLE_PARAM
tmp_table_param
;
bzero
((
char
*
)
&
tmp_table_param
,
sizeof
(
tmp_table_param
));
tmp_table_param
.
field_count
=
temp_fields
->
elements
;
if
(
!
(
tmp_tables
[
cnt
]
=
create_tmp_table
(
thd
,
&
tmp_table_param
,
*
temp_fields
,
(
ORDER
*
)
0
,
1
,
0
,
0
,
TMP_TABLE_ALL_COLUMNS
)))
if
(
!
(
tmp_tables
[
cnt
]
=
create_tmp_table
(
thd
,
&
tmp_table_param
,
*
temp_fields
,
(
ORDER
*
)
0
,
1
,
0
,
0
,
TMP_TABLE_ALL_COLUMNS
,
unit
)))
{
error
=
1
;
// A proper error message is due here
DBUG_RETURN
(
1
);
...
...
sql/sql_yacc.yy
View file @
ead6f225
...
...
@@ -1449,7 +1449,14 @@ select:
select_init:
SELECT_SYM select_part2 { Select->braces=false; } union
|
'(' SELECT_SYM select_part2 ')' { Select->braces=true;} union_opt
'(' SELECT_SYM select_part2 ')'
{
SELECT_LEX * sel=Select;
sel->braces=true;
/* select in braces, can't contain global parameters */
((SELECT_LEX_UNIT*)sel->master)->global_parameters=
sel->master;
} union_opt
select_part2:
...
...
@@ -3826,10 +3833,15 @@ optional_order_or_limit:
|
{
LEX *lex=Lex;
if (!lex->select->braces
|| mysql_new_select(lex, 0)
)
if (!lex->select->braces)
YYABORT;
mysql_init_select(lex);
lex->select->linkage= GLOBAL_OPTIONS_TYPE;
((SELECT_LEX_UNIT*)lex->select->master)->global_parameters=
lex->select->master;
/*
Following type conversion looks like hack, but all that need SELECT_LEX
fields always check linkage type.
*/
lex->select= (SELECT_LEX*)lex->select->master;
lex->select->select_limit=lex->thd->default_select_limit;
}
opt_order_clause limit_clause
...
...
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment