~drizzle-trunk/drizzle/development

390.1.2 by Monty Taylor
Fixed copyright headers in drizzled/
1
/* -*- mode: c++; c-basic-offset: 2; indent-tabs-mode: nil; -*-
2
 *  vim:expandtab:shiftwidth=2:tabstop=2:smarttab:
3
 *
4
 *  Copyright (C) 2008 Sun Microsystems
5
 *
6
 *  This program is free software; you can redistribute it and/or modify
7
 *  it under the terms of the GNU General Public License as published by
8
 *  the Free Software Foundation; version 2 of the License.
9
 *
10
 *  This program is distributed in the hope that it will be useful,
11
 *  but WITHOUT ANY WARRANTY; without even the implied warranty of
12
 *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
13
 *  GNU General Public License for more details.
14
 *
15
 *  You should have received a copy of the GNU General Public License
16
 *  along with this program; if not, write to the Free Software
17
 *  Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
18
 */
1 by brian
clean slate
19
575.1.6 by Monty Taylor
Cleaned up some headers for PCH.
20
#ifndef DRIZZLED_ITEM_SUBSELECT_H
21
#define DRIZZLED_ITEM_SUBSELECT_H
22
1 by brian
clean slate
23
/* subselect Item */
24
25
1237.9.3 by Padraig O'Sullivan
Removed one the includes I put in server_includes.h for the last commit to get rid of the inclusion
26
#include "drizzled/comp_creator.h"
27
#include "drizzled/item/ref.h"
28
#include "drizzled/item/field.h"
29
#include "drizzled/item/bin_string.h"
584.4.7 by Monty Taylor
Removed a big bank of includes from item.h.
30
1280.1.10 by Monty Taylor
Put everything in drizzled into drizzled namespace.
31
namespace drizzled
32
{
33
846 by Brian Aker
Removing on typedeffed class.
34
class Select_Lex;
848 by Brian Aker
typdef class removal (just... use the name of the class).
35
class Select_Lex_Unit;
1541.1.1 by Brian Aker
JOIN -> Join rename
36
class Join;
1 by brian
clean slate
37
class select_result_interceptor;
38
class subselect_engine;
39
class subselect_hash_sj_engine;
40
class Item_bool_func2;
41
class Cached_item;
584.4.7 by Monty Taylor
Removed a big bank of includes from item.h.
42
class Item_in_optimizer;
43
class Item_func_not_all;
851 by Brian Aker
Class rewrite of Session (aka get all of the junk out)
44
class Tmp_Table_Param;
584.4.7 by Monty Taylor
Removed a big bank of includes from item.h.
45
1 by brian
clean slate
46
47
/* base class for subselects */
48
49
class Item_subselect :public Item_result_field
50
{
275 by Brian Aker
Full removal of my_bool from central server.
51
  bool value_assigned; /* value already assigned to subselect */
1 by brian
clean slate
52
public:
53
  /* thread handler, will be assigned in fix_fields only */
520.1.22 by Brian Aker
Second pass of thd cleanup
54
  Session *session;
1 by brian
clean slate
55
  /* substitution instead of subselect in case of optimization */
56
  Item *substitution;
57
  /* unit of subquery */
848 by Brian Aker
typdef class removal (just... use the name of the class).
58
  Select_Lex_Unit *unit;
1 by brian
clean slate
59
protected:
60
  /* engine that perform execution of subselect (single select or union) */
61
  subselect_engine *engine;
62
  /* old engine if engine was changed */
63
  subselect_engine *old_engine;
64
  /* cache of used external tables */
65
  table_map used_tables_cache;
66
  /* allowed number of columns (1 for single value subqueries) */
482 by Brian Aker
Remove uint.
67
  uint32_t max_columns;
1 by brian
clean slate
68
  /* where subquery is placed */
69
  enum_parsing_place parsing_place;
70
  /* work with 'substitution' */
71
  bool have_to_be_excluded;
72
  /* cache of constant state */
73
  bool const_item_cache;
74
75
public:
76
  /* changed engine indicator */
77
  bool engine_changed;
78
  /* subquery is transformed */
79
  bool changed;
80
81
  /* TRUE <=> The underlying SELECT is correlated w.r.t some ancestor select */
660.1.3 by Eric Herman
removed trailing whitespace with simple script:
82
  bool is_correlated;
1 by brian
clean slate
83
84
  enum trans_res {RES_OK, RES_REDUCE, RES_ERROR};
85
  enum subs_type {UNKNOWN_SUBS, SINGLEROW_SUBS,
86
		  EXISTS_SUBS, IN_SUBS, ALL_SUBS, ANY_SUBS};
87
88
  Item_subselect();
89
90
  virtual subs_type substype() { return UNKNOWN_SUBS; }
91
92
  /*
93
    We need this method, because some compilers do not allow 'this'
94
    pointer in constructor initialization list, but we need to pass a pointer
95
    to subselect Item class to select_result_interceptor's constructor.
96
  */
846 by Brian Aker
Removing on typedeffed class.
97
  virtual void init (Select_Lex *select_lex,
1 by brian
clean slate
98
		     select_result_interceptor *result);
99
100
  ~Item_subselect();
101
  void cleanup();
102
  virtual void reset()
103
  {
104
    null_value= 1;
105
  }
1541.1.1 by Brian Aker
JOIN -> Join rename
106
  virtual trans_res select_transformer(Join *join);
1 by brian
clean slate
107
  bool assigned() { return value_assigned; }
108
  void assigned(bool a) { value_assigned= a; }
109
  enum Type type() const;
110
  bool is_null()
111
  {
112
    update_null_value();
113
    return null_value;
114
  }
520.1.22 by Brian Aker
Second pass of thd cleanup
115
  bool fix_fields(Session *session, Item **ref);
1 by brian
clean slate
116
  virtual bool exec();
117
  virtual void fix_length_and_dec();
118
  table_map used_tables() const;
119
  table_map not_null_tables() const { return 0; }
120
  bool const_item() const;
121
  inline table_map get_used_tables_cache() { return used_tables_cache; }
122
  inline bool get_const_item_cache() { return const_item_cache; }
520.1.22 by Brian Aker
Second pass of thd cleanup
123
  Item *get_tmp_table_item(Session *session);
1 by brian
clean slate
124
  void update_used_tables();
125
  virtual void print(String *str, enum_query_type query_type);
51.1.24 by Jay Pipes
Removed DBUG symbols and fixed TRUE/FALSE
126
  virtual bool have_guarded_conds() { return false; }
1 by brian
clean slate
127
  bool change_engine(subselect_engine *eng)
128
  {
129
    old_engine= engine;
130
    engine= eng;
131
    engine_changed= 1;
132
    return eng == 0;
133
  }
134
  /*
135
    True if this subquery has been already evaluated. Implemented only for
136
    single select and union subqueries only.
137
  */
138
  bool is_evaluated() const;
139
  bool is_uncacheable() const;
140
141
  /*
142
    Used by max/min subquery to initialize value presence registration
143
    mechanism. Engine call this method before rexecution query.
144
  */
145
  virtual void reset_value_registration() {}
146
  enum_parsing_place place() { return parsing_place; }
481 by Brian Aker
Remove all of uchar.
147
  bool walk(Item_processor processor, bool walk_subquery, unsigned char *arg);
1 by brian
clean slate
148
149
  /**
846 by Brian Aker
Removing on typedeffed class.
150
    Get the Select_Lex structure associated with this Item.
151
    @return the Select_Lex structure associated with this Item
1 by brian
clean slate
152
  */
846 by Brian Aker
Removing on typedeffed class.
153
  Select_Lex* get_select_lex();
1 by brian
clean slate
154
155
  friend class select_result_interceptor;
156
  friend class Item_in_optimizer;
520.1.21 by Brian Aker
THD -> Session rename
157
  friend bool Item_field::fix_fields(Session *, Item **);
158
  friend int  Item_field::fix_outer_field(Session *, Field **, Item **);
159
  friend bool Item_ref::fix_fields(Session *, Item **);
160
  friend void mark_select_range_as_dependent(Session*,
846 by Brian Aker
Removing on typedeffed class.
161
                                             Select_Lex*, Select_Lex*,
1 by brian
clean slate
162
                                             Field*, Item*, Item_ident*);
163
};
164
165
/* single value subselect */
166
167
class Item_cache;
168
class Item_singlerow_subselect :public Item_subselect
169
{
170
protected:
171
  Item_cache *value, **row;
172
public:
846 by Brian Aker
Removing on typedeffed class.
173
  Item_singlerow_subselect(Select_Lex *select_lex);
1 by brian
clean slate
174
  Item_singlerow_subselect() :Item_subselect(), value(0), row (0) {}
175
176
  void cleanup();
177
  subs_type substype() { return SINGLEROW_SUBS; }
178
179
  void reset();
1541.1.1 by Brian Aker
JOIN -> Join rename
180
  trans_res select_transformer(Join *join);
482 by Brian Aker
Remove uint.
181
  void store(uint32_t i, Item* item);
1 by brian
clean slate
182
  double val_real();
152 by Brian Aker
longlong replacement
183
  int64_t val_int ();
1 by brian
clean slate
184
  String *val_str (String *);
185
  my_decimal *val_decimal(my_decimal *);
186
  bool val_bool();
187
  enum Item_result result_type() const;
188
  enum_field_types field_type() const;
189
  void fix_length_and_dec();
190
482 by Brian Aker
Remove uint.
191
  uint32_t cols();
192
  Item* element_index(uint32_t i) { return reinterpret_cast<Item*>(row[i]); }
193
  Item** addr(uint32_t i) { return (Item**)row + i; }
194
  bool check_cols(uint32_t c);
1 by brian
clean slate
195
  bool null_inside();
196
  void bring_value();
197
198
  /**
199
    This method is used to implement a special case of semantic tree
200
    rewriting, mandated by a SQL:2003 exception in the specification.
201
    The only caller of this method is handle_sql2003_note184_exception(),
202
    see the code there for more details.
203
    Note that this method breaks the object internal integrity, by
846 by Brian Aker
Removing on typedeffed class.
204
    removing it's association with the corresponding Select_Lex,
1 by brian
clean slate
205
    making this object orphan from the parse tree.
206
    No other method, beside the destructor, should be called on this
207
    object, as it is now invalid.
846 by Brian Aker
Removing on typedeffed class.
208
    @return the Select_Lex structure that was given in the constructor.
1 by brian
clean slate
209
  */
846 by Brian Aker
Removing on typedeffed class.
210
  Select_Lex* invalidate_and_restore_select_lex();
1 by brian
clean slate
211
212
  friend class select_singlerow_subselect;
213
};
214
215
/* used in static ALL/ANY optimization */
216
class select_max_min_finder_subselect;
217
class Item_maxmin_subselect :public Item_singlerow_subselect
218
{
219
protected:
220
  bool max;
221
  bool was_values;  // Set if we have found at least one row
222
public:
520.1.22 by Brian Aker
Second pass of thd cleanup
223
  Item_maxmin_subselect(Session *session, Item_subselect *parent,
846 by Brian Aker
Removing on typedeffed class.
224
			Select_Lex *select_lex, bool max);
1 by brian
clean slate
225
  virtual void print(String *str, enum_query_type query_type);
226
  void cleanup();
227
  bool any_value() { return was_values; }
51.1.24 by Jay Pipes
Removed DBUG symbols and fixed TRUE/FALSE
228
  void register_value() { was_values= true; }
229
  void reset_value_registration() { was_values= false; }
1 by brian
clean slate
230
};
231
232
/* exists subselect */
233
234
class Item_exists_subselect :public Item_subselect
235
{
236
protected:
237
  bool value; /* value of this item (boolean: exists/not-exists) */
238
239
public:
846 by Brian Aker
Removing on typedeffed class.
240
  Item_exists_subselect(Select_Lex *select_lex);
1 by brian
clean slate
241
  Item_exists_subselect(): Item_subselect() {}
242
243
  subs_type substype() { return EXISTS_SUBS; }
660.1.3 by Eric Herman
removed trailing whitespace with simple script:
244
  void reset()
1 by brian
clean slate
245
  {
246
    value= 0;
247
  }
248
249
  enum Item_result result_type() const { return INT_RESULT;}
152 by Brian Aker
longlong replacement
250
  int64_t val_int();
1 by brian
clean slate
251
  double val_real();
252
  String *val_str(String*);
253
  my_decimal *val_decimal(my_decimal *);
254
  bool val_bool();
255
  void fix_length_and_dec();
256
  virtual void print(String *str, enum_query_type query_type);
257
258
  friend class select_exists_subselect;
259
  friend class subselect_uniquesubquery_engine;
260
  friend class subselect_indexsubquery_engine;
261
};
262
263
264
/**
265
  Representation of IN subquery predicates of the form
266
  "left_expr IN (SELECT ...)".
267
268
  @detail
660.1.3 by Eric Herman
removed trailing whitespace with simple script:
269
  This class has:
1 by brian
clean slate
270
   - A "subquery execution engine" (as a subclass of Item_subselect) that allows
271
     it to evaluate subqueries. (and this class participates in execution by
272
     having was_null variable where part of execution result is stored.
273
   - Transformation methods (todo: more on this).
274
275
  This class is not used directly, it is "wrapped" into Item_in_optimizer
276
  which provides some small bits of subquery evaluation.
277
*/
278
279
class Item_in_subselect :public Item_exists_subselect
280
{
281
public:
282
  Item *left_expr;
283
protected:
284
  /*
285
    Cache of the left operand of the subquery predicate. Allocated in the
286
    runtime memory root, for each execution, thus need not be freed.
287
  */
1101.1.16 by Monty Taylor
Reverted 1103
288
  List<Cached_item> *left_expr_cache;
1 by brian
clean slate
289
  bool first_execution;
290
291
  /*
292
    expr & optimizer used in subselect rewriting to store Item for
293
    all JOIN in UNION
294
  */
295
  Item *expr;
296
  Item_in_optimizer *optimizer;
297
  bool was_null;
298
  bool abort_on_null;
299
300
public:
301
  /* Used to trigger on/off conditions that were pushed down to subselect */
302
  bool *pushed_cond_guards;
660.1.3 by Eric Herman
removed trailing whitespace with simple script:
303
1 by brian
clean slate
304
  /* Priority of this predicate in the convert-to-semi-join-nest process. */
305
  int sj_convert_priority;
306
660.1.3 by Eric Herman
removed trailing whitespace with simple script:
307
  /*
1 by brian
clean slate
308
    Location of the subquery predicate. It is either
309
     - pointer to join nest if the subquery predicate is in the ON expression
327.2.4 by Brian Aker
Refactoring table.h
310
     - (TableList*)1 if the predicate is in the WHERE.
1 by brian
clean slate
311
  */
327.2.4 by Brian Aker
Refactoring table.h
312
  TableList *expr_join_nest;
1 by brian
clean slate
313
314
  /* The method chosen to execute the IN predicate.  */
315
  enum enum_exec_method {
316
    NOT_TRANSFORMED, /* No execution method was chosen for this IN. */
317
    SEMI_JOIN,   /* IN was converted to semi-join nest and should be removed. */
318
    IN_TO_EXISTS, /* IN was converted to correlated EXISTS. */
319
    MATERIALIZATION /* IN will be executed via subquery materialization. */
320
  };
321
  enum_exec_method exec_method;
322
323
  bool *get_cond_guard(int i)
324
  {
325
    return pushed_cond_guards ? pushed_cond_guards + i : NULL;
326
  }
660.1.3 by Eric Herman
removed trailing whitespace with simple script:
327
  void set_cond_guard_var(int i, bool v)
328
  {
1 by brian
clean slate
329
    if ( pushed_cond_guards)
330
      pushed_cond_guards[i]= v;
331
  }
1637.5.4 by Prafulla Tekawade
Reverting some un-necessary changes.
332
  bool have_guarded_conds() { return test(pushed_cond_guards); }
1 by brian
clean slate
333
334
  Item_func_not_all *upper_item; // point on NOT/NOP before ALL/SOME subquery
335
846 by Brian Aker
Removing on typedeffed class.
336
  Item_in_subselect(Item * left_expr, Select_Lex *select_lex);
1 by brian
clean slate
337
  Item_in_subselect()
1221.1.1 by Jay Pipes
Fixes some valgrind warnings regarding conditionals depending on unintialized variables. Use initializer lists properly, dang it. :) Also, removed the new_Cached_item() function's use_result_field, as this was only used for views and was producing a valgrind warning unnecessarily.
338
    :
339
      Item_exists_subselect(),
340
      left_expr(NULL),
341
      left_expr_cache(NULL),
342
      first_execution(true),
343
      optimizer(NULL),
344
      abort_on_null(false),
345
      pushed_cond_guards(NULL),
346
      sj_convert_priority(0),
347
      expr_join_nest(NULL),
348
      exec_method(NOT_TRANSFORMED),
349
      upper_item(NULL)
1 by brian
clean slate
350
  {}
351
  void cleanup();
352
  subs_type substype() { return IN_SUBS; }
660.1.3 by Eric Herman
removed trailing whitespace with simple script:
353
  void reset()
1 by brian
clean slate
354
  {
355
    value= 0;
356
    null_value= 0;
357
    was_null= 0;
358
  }
1541.1.1 by Brian Aker
JOIN -> Join rename
359
  trans_res select_transformer(Join *join);
360
  trans_res select_in_like_transformer(Join *join, const Comp_creator *func);
361
  trans_res single_value_transformer(Join *join, const Comp_creator *func);
362
  trans_res row_value_transformer(Join * join);
363
  trans_res single_value_in_to_exists_transformer(Join * join,
584.4.7 by Monty Taylor
Removed a big bank of includes from item.h.
364
                                                  const Comp_creator *func);
1541.1.1 by Brian Aker
JOIN -> Join rename
365
  trans_res row_value_in_to_exists_transformer(Join * join);
1 by brian
clean slate
366
  virtual bool exec();
152 by Brian Aker
longlong replacement
367
  int64_t val_int();
1 by brian
clean slate
368
  double val_real();
369
  String *val_str(String*);
370
  my_decimal *val_decimal(my_decimal *);
371
  void update_null_value () { (void) val_bool(); }
372
  bool val_bool();
373
  void top_level_item() { abort_on_null=1; }
374
  inline bool is_top_level_item() { return abort_on_null; }
848 by Brian Aker
typdef class removal (just... use the name of the class).
375
  bool test_limit(Select_Lex_Unit *unit);
1 by brian
clean slate
376
  virtual void print(String *str, enum_query_type query_type);
520.1.22 by Brian Aker
Second pass of thd cleanup
377
  bool fix_fields(Session *session, Item **ref);
1 by brian
clean slate
378
  bool setup_engine();
379
  bool init_left_expr_cache();
481 by Brian Aker
Remove all of uchar.
380
  bool is_expensive_processor(unsigned char *arg);
1 by brian
clean slate
381
382
  friend class Item_ref_null_helper;
383
  friend class Item_is_not_null_test;
384
  friend class Item_in_optimizer;
385
  friend class subselect_indexsubquery_engine;
386
  friend class subselect_hash_sj_engine;
387
};
388
389
390
/* ALL/ANY/SOME subselect */
391
class Item_allany_subselect :public Item_in_subselect
392
{
393
public:
394
  chooser_compare_func_creator func_creator;
395
  Comp_creator *func;
396
  bool all;
397
398
  Item_allany_subselect(Item * left_expr, chooser_compare_func_creator fc,
846 by Brian Aker
Removing on typedeffed class.
399
                        Select_Lex *select_lex, bool all);
1 by brian
clean slate
400
401
  // only ALL subquery has upper not
402
  subs_type substype() { return all?ALL_SUBS:ANY_SUBS; }
1541.1.1 by Brian Aker
JOIN -> Join rename
403
  trans_res select_transformer(Join *join);
1 by brian
clean slate
404
  virtual void print(String *str, enum_query_type query_type);
405
};
406
407
1280.1.10 by Monty Taylor
Put everything in drizzled into drizzled namespace.
408
class subselect_engine: public memory::SqlAlloc
1 by brian
clean slate
409
{
410
protected:
411
  select_result_interceptor *result; /* results storage class */
520.1.22 by Brian Aker
Second pass of thd cleanup
412
  Session *session; /* pointer to current Session */
1 by brian
clean slate
413
  Item_subselect *item; /* item, that use this engine */
414
  enum Item_result res_type; /* type of results */
415
  enum_field_types res_field_type; /* column type of the results */
416
  bool maybe_null; /* may be null (first item in select) */
417
public:
418
419
  enum enum_engine_type {ABSTRACT_ENGINE, SINGLE_SELECT_ENGINE,
420
                         UNION_ENGINE, UNIQUESUBQUERY_ENGINE,
421
                         INDEXSUBQUERY_ENGINE, HASH_SJ_ENGINE};
422
423
  subselect_engine(Item_subselect *si, select_result_interceptor *res)
1280.1.10 by Monty Taylor
Put everything in drizzled into drizzled namespace.
424
    :session(NULL)
1 by brian
clean slate
425
  {
426
    result= res;
427
    item= si;
428
    res_type= STRING_RESULT;
241 by Brian Aker
First pass of CHAR removal.
429
    res_field_type= DRIZZLE_TYPE_VARCHAR;
1 by brian
clean slate
430
    maybe_null= 0;
431
  }
432
  virtual ~subselect_engine() {}; // to satisfy compiler
433
  virtual void cleanup()= 0;
434
435
  /*
520.1.22 by Brian Aker
Second pass of thd cleanup
436
    Also sets "session" for subselect_engine::result.
1 by brian
clean slate
437
    Should be called before prepare().
438
  */
520.1.22 by Brian Aker
Second pass of thd cleanup
439
  void set_session(Session *session_arg);
440
  Session * get_session() { return session; }
1 by brian
clean slate
441
  virtual int prepare()= 0;
442
  virtual void fix_length_and_dec(Item_cache** row)= 0;
443
  /*
444
    Execute the engine
445
446
    SYNOPSIS
447
      exec()
448
449
    DESCRIPTION
450
      Execute the engine. The result of execution is subquery value that is
451
      either captured by previously set up select_result-based 'sink' or
452
      stored somewhere by the exec() method itself.
453
454
      A required side effect: If at least one pushed-down predicate is
660.1.3 by Eric Herman
removed trailing whitespace with simple script:
455
      disabled, subselect_engine->no_rows() must return correct result after
1 by brian
clean slate
456
      the exec() call.
457
458
    RETURN
459
      0 - OK
460
      1 - Either an execution error, or the engine was "changed", and the
461
          caller should call exec() again for the new engine.
462
  */
463
  virtual int exec()= 0;
482 by Brian Aker
Remove uint.
464
  virtual uint32_t cols()= 0; /* return number of columns in select */
206 by Brian Aker
Removed final uint dead types.
465
  virtual uint8_t uncacheable()= 0; /* query is uncacheable */
1 by brian
clean slate
466
  enum Item_result type() { return res_type; }
467
  enum_field_types field_type() { return res_field_type; }
468
  virtual void exclude()= 0;
469
  virtual bool may_be_null() { return maybe_null; };
470
  virtual table_map upper_select_const_tables()= 0;
327.2.4 by Brian Aker
Refactoring table.h
471
  static table_map calc_const_tables(TableList *);
1 by brian
clean slate
472
  virtual void print(String *str, enum_query_type query_type)= 0;
473
  virtual bool change_result(Item_subselect *si,
474
                             select_result_interceptor *result)= 0;
475
  virtual bool no_tables()= 0;
51.1.24 by Jay Pipes
Removed DBUG symbols and fixed TRUE/FALSE
476
  virtual bool is_executed() const { return false; }
1 by brian
clean slate
477
  /* Check if subquery produced any rows during last query execution */
478
  virtual bool no_rows() = 0;
479
  virtual enum_engine_type engine_type() { return ABSTRACT_ENGINE; }
480
481
protected:
482
  void set_row(List<Item> &item_list, Item_cache **row);
483
};
484
485
486
class subselect_single_select_engine: public subselect_engine
487
{
275 by Brian Aker
Full removal of my_bool from central server.
488
  bool prepared; /* simple subselect is prepared */
489
  bool optimized; /* simple subselect is optimized */
490
  bool executed; /* simple subselect is executed */
846 by Brian Aker
Removing on typedeffed class.
491
  Select_Lex *select_lex; /* corresponding select_lex */
1541.1.1 by Brian Aker
JOIN -> Join rename
492
  Join * join; /* corresponding JOIN structure */
1 by brian
clean slate
493
public:
846 by Brian Aker
Removing on typedeffed class.
494
  subselect_single_select_engine(Select_Lex *select,
1 by brian
clean slate
495
				 select_result_interceptor *result,
496
				 Item_subselect *item);
497
  void cleanup();
498
  int prepare();
499
  void fix_length_and_dec(Item_cache** row);
500
  int exec();
482 by Brian Aker
Remove uint.
501
  uint32_t cols();
206 by Brian Aker
Removed final uint dead types.
502
  uint8_t uncacheable();
1 by brian
clean slate
503
  void exclude();
504
  table_map upper_select_const_tables();
505
  virtual void print (String *str, enum_query_type query_type);
506
  bool change_result(Item_subselect *si, select_result_interceptor *result);
507
  bool no_tables();
508
  bool may_be_null();
509
  bool is_executed() const { return executed; }
510
  bool no_rows();
511
  virtual enum_engine_type engine_type() { return SINGLE_SELECT_ENGINE; }
512
513
  friend class subselect_hash_sj_engine;
514
  friend class Item_in_subselect;
515
};
516
517
518
class subselect_union_engine: public subselect_engine
519
{
848 by Brian Aker
typdef class removal (just... use the name of the class).
520
  Select_Lex_Unit *unit;  /* corresponding unit structure */
1 by brian
clean slate
521
public:
848 by Brian Aker
typdef class removal (just... use the name of the class).
522
  subselect_union_engine(Select_Lex_Unit *u,
1 by brian
clean slate
523
			 select_result_interceptor *result,
524
			 Item_subselect *item);
525
  void cleanup();
526
  int prepare();
527
  void fix_length_and_dec(Item_cache** row);
528
  int exec();
482 by Brian Aker
Remove uint.
529
  uint32_t cols();
206 by Brian Aker
Removed final uint dead types.
530
  uint8_t uncacheable();
1 by brian
clean slate
531
  void exclude();
532
  table_map upper_select_const_tables();
533
  virtual void print (String *str, enum_query_type query_type);
534
  bool change_result(Item_subselect *si, select_result_interceptor *result);
535
  bool no_tables();
536
  bool is_executed() const;
537
  bool no_rows();
538
  virtual enum_engine_type engine_type() { return UNION_ENGINE; }
539
};
540
541
1089.1.1 by Brian Aker
Remove of JOIN_TAB to JoinTable
542
class JoinTable;
1 by brian
clean slate
543
544
545
/*
546
  A subquery execution engine that evaluates the subquery by doing one index
547
  lookup in a unique index.
548
549
  This engine is used to resolve subqueries in forms
660.1.3 by Eric Herman
removed trailing whitespace with simple script:
550
551
    outer_expr IN (SELECT tbl.unique_key FROM tbl WHERE subq_where)
552
1 by brian
clean slate
553
  or, tuple-based:
660.1.3 by Eric Herman
removed trailing whitespace with simple script:
554
1 by brian
clean slate
555
    (oe1, .. oeN) IN (SELECT uniq_key_part1, ... uniq_key_partK
660.1.3 by Eric Herman
removed trailing whitespace with simple script:
556
                      FROM tbl WHERE subqwhere)
557
1 by brian
clean slate
558
  i.e. the subquery is a single table SELECT without GROUP BY, aggregate
559
  functions, etc.
560
*/
561
562
class subselect_uniquesubquery_engine: public subselect_engine
563
{
564
protected:
1089.1.1 by Brian Aker
Remove of JOIN_TAB to JoinTable
565
  JoinTable *tab;
1 by brian
clean slate
566
  Item *cond; /* The WHERE condition of subselect */
660.1.3 by Eric Herman
removed trailing whitespace with simple script:
567
  /*
1 by brian
clean slate
568
    TRUE<=> last execution produced empty set. Valid only when left
569
    expression is NULL.
570
  */
571
  bool empty_result_set;
572
  bool null_keypart; /* TRUE <=> constructed search tuple has a NULL */
573
public:
574
1541.1.1 by Brian Aker
JOIN -> Join rename
575
  // constructor can assign Session because it will be called after Join::prepare
1089.1.1 by Brian Aker
Remove of JOIN_TAB to JoinTable
576
  subselect_uniquesubquery_engine(Session *session_arg, JoinTable *tab_arg,
1 by brian
clean slate
577
				  Item_subselect *subs, Item *where)
578
    :subselect_engine(subs, 0), tab(tab_arg), cond(where)
579
  {
520.1.22 by Brian Aker
Second pass of thd cleanup
580
    set_session(session_arg);
1 by brian
clean slate
581
  }
582
  void cleanup();
583
  int prepare();
584
  void fix_length_and_dec(Item_cache** row);
585
  int exec();
482 by Brian Aker
Remove uint.
586
  uint32_t cols() { return 1; }
206 by Brian Aker
Removed final uint dead types.
587
  uint8_t uncacheable() { return UNCACHEABLE_DEPENDENT; }
1 by brian
clean slate
588
  void exclude();
589
  table_map upper_select_const_tables() { return 0; }
590
  virtual void print (String *str, enum_query_type query_type);
591
  bool change_result(Item_subselect *si, select_result_interceptor *result);
592
  bool no_tables();
593
  int scan_table();
594
  bool copy_ref_key();
595
  bool no_rows() { return empty_result_set; }
596
  virtual enum_engine_type engine_type() { return UNIQUESUBQUERY_ENGINE; }
597
};
598
599
600
class subselect_indexsubquery_engine: public subselect_uniquesubquery_engine
601
{
602
  /* FALSE for 'ref', TRUE for 'ref-or-null'. */
603
  bool check_null;
660.1.3 by Eric Herman
removed trailing whitespace with simple script:
604
  /*
1 by brian
clean slate
605
    The "having" clause. This clause (further reffered to as "artificial
660.1.3 by Eric Herman
removed trailing whitespace with simple script:
606
    having") was inserted by subquery transformation code. It contains
607
    Item(s) that have a side-effect: they record whether the subquery has
1 by brian
clean slate
608
    produced a row with NULL certain components. We need to use it for cases
609
    like
610
      (oe1, oe2) IN (SELECT t.key, t.no_key FROM t1)
611
    where we do index lookup on t.key=oe1 but need also to check if there
612
    was a row such that t.no_key IS NULL.
660.1.3 by Eric Herman
removed trailing whitespace with simple script:
613
1 by brian
clean slate
614
    NOTE: This is currently here and not in the uniquesubquery_engine. Ideally
615
    it should have been in uniquesubquery_engine in order to allow execution of
616
    subqueries like
660.1.3 by Eric Herman
removed trailing whitespace with simple script:
617
1 by brian
clean slate
618
      (oe1, oe2) IN (SELECT primary_key, non_key_maybe_null_field FROM tbl)
619
620
    We could use uniquesubquery_engine for the first component and let
621
    Item_is_not_null_test( non_key_maybe_null_field) to handle the second.
622
623
    However, subqueries like the above are currently not handled by index
624
    lookup-based subquery engines, the engine applicability check misses
625
    them: it doesn't switch the engine for case of artificial having and
626
    [eq_]ref access (only for artifical having + ref_or_null or no having).
627
    The above example subquery is handled as a full-blown SELECT with eq_ref
628
    access to one table.
629
660.1.3 by Eric Herman
removed trailing whitespace with simple script:
630
    Due to this limitation, the "artificial having" currently needs to be
1 by brian
clean slate
631
    checked by only in indexsubquery_engine.
632
  */
633
  Item *having;
634
public:
635
1541.1.1 by Brian Aker
JOIN -> Join rename
636
  // constructor can assign Session because it will be called after Join::prepare
1089.1.1 by Brian Aker
Remove of JOIN_TAB to JoinTable
637
  subselect_indexsubquery_engine(Session *session_arg, JoinTable *tab_arg,
1 by brian
clean slate
638
				 Item_subselect *subs, Item *where,
639
                                 Item *having_arg, bool chk_null)
520.1.22 by Brian Aker
Second pass of thd cleanup
640
    :subselect_uniquesubquery_engine(session_arg, tab_arg, subs, where),
1 by brian
clean slate
641
     check_null(chk_null),
642
     having(having_arg)
643
  {}
644
  int exec();
645
  virtual void print (String *str, enum_query_type query_type);
646
  virtual enum_engine_type engine_type() { return INDEXSUBQUERY_ENGINE; }
647
};
648
649
650
inline bool Item_subselect::is_evaluated() const
651
{
652
  return engine->is_executed();
653
}
654
655
656
inline bool Item_subselect::is_uncacheable() const
657
{
658
  return engine->uncacheable();
659
}
660
661
662
/**
663
  Compute an IN predicate via a hash semi-join. The subquery is materialized
664
  during the first evaluation of the IN predicate. The IN predicate is executed
665
  via the functionality inherited from subselect_uniquesubquery_engine.
666
*/
667
668
class subselect_hash_sj_engine: public subselect_uniquesubquery_engine
669
{
670
protected:
671
  /* TRUE if the subquery was materialized into a temp table. */
672
  bool is_materialized;
673
  /*
674
    The old engine already chosen at parse time and stored in permanent memory.
675
    Through this member we can re-create and re-prepare materialize_join for
676
    each execution of a prepared statement. We akso resuse the functionality
677
    of subselect_single_select_engine::[prepare | cols].
678
  */
679
  subselect_single_select_engine *materialize_engine;
680
  /*
681
    QEP to execute the subquery and materialize its result into a
682
    temporary table. Created during the first call to exec().
683
  */
1541.1.1 by Brian Aker
JOIN -> Join rename
684
  Join *materialize_join;
1 by brian
clean slate
685
  /* Temp table context of the outer select's JOIN. */
851 by Brian Aker
Class rewrite of Session (aka get all of the junk out)
686
  Tmp_Table_Param *tmp_param;
1 by brian
clean slate
687
688
public:
779.3.10 by Monty Taylor
Turned on -Wshadow.
689
  subselect_hash_sj_engine(Session *session_in, Item_subselect *in_predicate,
1 by brian
clean slate
690
                               subselect_single_select_engine *old_engine)
779.3.10 by Monty Taylor
Turned on -Wshadow.
691
    :subselect_uniquesubquery_engine(session_in, NULL, in_predicate, NULL),
51.1.24 by Jay Pipes
Removed DBUG symbols and fixed TRUE/FALSE
692
    is_materialized(false), materialize_engine(old_engine),
1 by brian
clean slate
693
    materialize_join(NULL), tmp_param(NULL)
694
  {}
695
  ~subselect_hash_sj_engine();
696
697
  bool init_permanent(List<Item> *tmp_columns);
698
  bool init_runtime();
699
  void cleanup();
700
  int prepare() { return 0; }
701
  int exec();
702
  virtual void print (String *str, enum_query_type query_type);
482 by Brian Aker
Remove uint.
703
  uint32_t cols()
1 by brian
clean slate
704
  {
705
    return materialize_engine->cols();
706
  }
707
  virtual enum_engine_type engine_type() { return HASH_SJ_ENGINE; }
708
};
575.1.6 by Monty Taylor
Cleaned up some headers for PCH.
709
1280.1.10 by Monty Taylor
Put everything in drizzled into drizzled namespace.
710
} /* namespace drizzled */
711
575.1.6 by Monty Taylor
Cleaned up some headers for PCH.
712
#endif /* DRIZZLED_ITEM_SUBSELECT_H */