18
18
UNION's were introduced by Monty and Sinisa <sinisa@mysql.com>
22
21
#include <drizzled/sql_select.h>
23
22
#include <drizzled/error.h>
24
23
#include <drizzled/item/type_holder.h>
25
24
#include <drizzled/sql_base.h>
26
25
#include <drizzled/sql_union.h>
27
#include <drizzled/select_union.h>
28
#include <drizzled/sql_lex.h>
29
#include <drizzled/session.h>
30
#include <drizzled/item/subselect.h>
34
30
bool drizzle_union(Session *session, LEX *, select_result *result,
35
31
Select_Lex_Unit *unit, uint64_t setup_tables_done_option)
37
bool res= unit->prepare(session, result, SELECT_NO_UNLOCK | setup_tables_done_option);
34
if (!(res= unit->prepare(session, result, SELECT_NO_UNLOCK |
35
setup_tables_done_option)))
38
res|= unit->cleanup();
126
123
assert(table == NULL);
127
124
tmp_table_param.init();
128
tmp_table_param.field_count= column_types->size();
125
tmp_table_param.field_count= column_types->elements;
130
127
if (! (table= create_tmp_table(session_arg, &tmp_table_param, *column_types,
131
128
(Order*) NULL, is_union_distinct, 1,
172
169
Select_Lex_Unit::init_prepare_fake_select_lex(Session *session_arg)
174
session_arg->lex().current_select= fake_select_lex;
171
session_arg->lex->current_select= fake_select_lex;
175
172
fake_select_lex->table_list.link_in_list((unsigned char *)&result_table_list,
176
173
(unsigned char **)
177
174
&result_table_list.next_local);
197
194
bool Select_Lex_Unit::prepare(Session *session_arg, select_result *sel_result,
198
195
uint64_t additional_options)
200
Select_Lex *lex_select_save= session_arg->lex().current_select;
197
Select_Lex *lex_select_save= session_arg->lex->current_select;
201
198
Select_Lex *sl, *first_sl= first_select();
202
199
select_result *tmp_result;
203
200
bool is_union_select;
223
220
offset_limit_cnt= 0;
224
221
if (result->prepare(sl->join->fields_list, this))
228
225
sl->join->select_options|= SELECT_DESCRIBE;
229
226
sl->join->reinit();
235
232
saved_error= false;
237
session_arg->lex().current_select= sl= first_sl;
234
session_arg->lex->current_select= sl= first_sl;
238
235
found_rows_for_union= first_sl->options & OPTION_FOUND_ROWS;
239
236
is_union_select= is_union() || fake_select_lex;
304
302
field object without table.
306
304
assert(!empty_table);
307
empty_table= (Table*) session->mem.calloc(sizeof(Table));
309
List<Item>::iterator it(sl->item_list.begin());
310
while (Item* item_tmp= it++)
305
empty_table= (Table*) session->calloc(sizeof(Table));
307
List_iterator_fast<Item> it(sl->item_list);
309
while ((item_tmp= it++))
312
311
/* Error's in 'new' will be detected after loop */
313
312
types.push_back(new Item_type_holder(session_arg, item_tmp));
321
if (types.size() != sl->item_list.size())
320
if (types.elements != sl->item_list.elements)
323
322
my_message(ER_WRONG_NUMBER_OF_COLUMNS_IN_SELECT,
324
323
ER(ER_WRONG_NUMBER_OF_COLUMNS_IN_SELECT),MYF(0));
327
List<Item>::iterator it(sl->item_list.begin());
328
List<Item>::iterator tp(types.begin());
326
List_iterator_fast<Item> it(sl->item_list);
327
List_iterator_fast<Item> tp(types);
329
328
Item *type, *item_tmp;
330
329
while ((type= tp++, item_tmp= it++))
332
331
if (((Item_type_holder*)type)->join_types(session_arg, item_tmp))
358
create_options= first_sl->options | session_arg->options | TMP_TABLE_ALL_COLUMNS;
357
create_options= (first_sl->options | session_arg->options |
358
TMP_TABLE_ALL_COLUMNS);
360
if (union_result->create_result_table(session, &types, test(union_distinct), create_options, ""))
360
if (union_result->create_result_table(session, &types, test(union_distinct),
362
363
memset(&result_table_list, 0, sizeof(result_table_list));
363
result_table_list.setSchemaName("");
364
result_table_list.setSchemaName((char*) "");
364
365
result_table_list.alias= "union";
365
result_table_list.setTableName("union");
366
result_table_list.setTableName((char *) "union");
366
367
result_table_list.table= table= union_result->table;
368
session_arg->lex().current_select= lex_select_save;
369
if (item_list.is_empty())
370
table->fill_item_list(item_list);
369
session_arg->lex->current_select= lex_select_save;
370
if (!item_list.elements)
372
saved_error= table->fill_item_list(&item_list);
374
379
We're in execution of a prepared statement or stored procedure:
375
380
reset field items to point at fields from the created temporary table.
381
session_arg->lex().current_select= lex_select_save;
386
session_arg->lex->current_select= lex_select_save;
383
388
return(saved_error || session_arg->is_fatal_error);
386
session_arg->lex().current_select= lex_select_save;
391
session_arg->lex->current_select= lex_select_save;
391
396
bool Select_Lex_Unit::exec()
393
Select_Lex *lex_select_save= session->lex().current_select;
398
Select_Lex *lex_select_save= session->lex->current_select;
394
399
Select_Lex *select_cursor=first_select();
395
400
uint64_t add_rows=0;
396
401
ha_rows examined_rows= 0;
420
425
for (Select_Lex *sl= select_cursor; sl; sl= sl->next_select())
422
427
ha_rows records_at_start= 0;
423
session->lex().current_select= sl;
428
session->lex->current_select= sl;
426
431
saved_error= sl->join->reinit();
468
473
examined_rows+= session->examined_row_count;
469
474
if (union_result->flush())
471
session->lex().current_select= lex_select_save;
476
session->lex->current_select= lex_select_save;
478
session->lex().current_select= lex_select_save;
483
session->lex->current_select= lex_select_save;
479
484
return(saved_error);
481
486
/* Needed for the following test and for records_at_start in next loop */
515
520
allocate JOIN for fake select only once (prevent
516
select_query automatic allocation)
517
TODO: The above is nonsense. select_query() will not allocate the
521
mysql_select automatic allocation)
522
TODO: The above is nonsense. mysql_select() will not allocate the
518
523
join if one already exists. There must be some other reason why we
519
524
don't let it allocate the join. Perhaps this is because we need
520
525
some special parameter values passed to join constructor?
522
fake_select_lex->join= new Join(session, item_list, fake_select_lex->options, result);
523
fake_select_lex->join->no_const_tables= true;
527
if (!(fake_select_lex->join= new Join(session, item_list,
528
fake_select_lex->options, result)))
530
fake_select_lex->table_list.empty();
533
fake_select_lex->join->no_const_tables= true;
526
536
Fake Select_Lex should have item list for correctref_array
529
539
fake_select_lex->item_list= item_list;
530
saved_error= select_query(session, &fake_select_lex->ref_pointer_array,
540
saved_error= mysql_select(session, &fake_select_lex->ref_pointer_array,
531
541
&result_table_list,
532
542
0, item_list, NULL,
533
global_parameters->order_list.size(),
543
global_parameters->order_list.elements,
534
544
(Order*)global_parameters->order_list.first,
535
545
(Order*) NULL, NULL,
536
546
fake_select_lex->options | SELECT_NO_UNLOCK,
550
560
to reset them back, we re-do all of the actions (yes it is ugly):
552
562
join->reset(session, item_list, fake_select_lex->options, result);
553
saved_error= select_query(session, &fake_select_lex->ref_pointer_array,
563
saved_error= mysql_select(session, &fake_select_lex->ref_pointer_array,
554
564
&result_table_list,
555
565
0, item_list, NULL,
556
global_parameters->order_list.size(),
566
global_parameters->order_list.elements,
557
567
(Order*)global_parameters->order_list.first,
558
568
(Order*) NULL, NULL,
559
569
fake_select_lex->options | SELECT_NO_UNLOCK,
699
710
assert((Select_Lex*)join->select_lex == this);
700
711
error= join->destroy();
703
715
for (Select_Lex_Unit *lex_unit= first_inner_unit(); lex_unit ;
704
716
lex_unit= lex_unit->next_unit())
706
718
error= (bool) ((uint32_t) error | (uint32_t) lex_unit->cleanup());
708
non_agg_fields.clear();
709
inner_refs_list.clear();
720
non_agg_fields.empty();
721
inner_refs_list.empty();