~drizzle-trunk/drizzle/development

« back to all changes in this revision

Viewing changes to drizzled/item_subselect.cc

code clean move Item_func_abs, Item_func_int_exp, Item_func_ln, Item_func_log to functions directory

Show diffs side-by-side

added added

removed removed

Lines of Context:
23
23
    - add function from mysql_select that use JOIN* as parameter to JOIN
24
24
    methods (sql_select.h/sql_select.cc)
25
25
*/
26
 
#include "config.h"
27
 
 
28
 
#include <limits.h>
29
 
 
 
26
#include <drizzled/server_includes.h>
30
27
#include <drizzled/sql_select.h>
31
 
#include <drizzled/error.h>
32
 
#include <drizzled/item/cache.h>
33
 
#include <drizzled/item/subselect.h>
34
 
#include <drizzled/item/cmpfunc.h>
35
 
#include <drizzled/item/ref_null_helper.h>
36
 
#include <drizzled/cached_item.h>
37
 
#include <drizzled/check_stack_overrun.h>
38
 
#include <drizzled/item/ref_null_helper.h>
39
 
#include <drizzled/item/direct_ref.h>
40
 
#include <drizzled/join.h>
41
 
 
42
 
namespace drizzled
43
 
{
44
 
 
45
 
extern plugin::StorageEngine *myisam_engine;
 
28
#include <drizzled/drizzled_error_messages.h>
46
29
 
47
30
inline Item * and_items(Item* cond, Item *item)
48
31
{
49
32
  return (cond? (new Item_cond_and(cond, item)) : item);
50
33
}
51
34
 
52
 
Item_subselect::Item_subselect() :
53
 
  Item_result_field(),
54
 
  value_assigned(false),
55
 
  session(NULL),
56
 
  substitution(NULL),
57
 
  unit(NULL),
58
 
  engine(NULL),
59
 
  old_engine(NULL),
60
 
  used_tables_cache(0),
61
 
  max_columns(0),
62
 
  parsing_place(NO_MATTER),
63
 
  have_to_be_excluded(false),
64
 
  const_item_cache(true),
65
 
  engine_changed(false),
66
 
  changed(false),
 
35
Item_subselect::Item_subselect():
 
36
  Item_result_field(), value_assigned(0), thd(0), substitution(0),
 
37
  engine(0), old_engine(0), used_tables_cache(0), have_to_be_excluded(0),
 
38
  const_item_cache(1), engine_changed(0), changed(0),
67
39
  is_correlated(false)
68
40
{
69
41
  with_subselect= 1;
76
48
}
77
49
 
78
50
 
79
 
void Item_subselect::init(Select_Lex *select_lex,
 
51
void Item_subselect::init(st_select_lex *select_lex,
80
52
                          select_result_interceptor *result)
81
53
{
82
54
  /*
100
72
  }
101
73
  else
102
74
  {
103
 
    Select_Lex *outer_select= unit->outer_select();
 
75
    SELECT_LEX *outer_select= unit->outer_select();
104
76
    /*
105
77
      do not take into account expression inside aggregate functions because
106
78
      they can access original table fields
114
86
      engine= new subselect_single_select_engine(select_lex, result, this);
115
87
  }
116
88
  {
117
 
    Select_Lex *upper= unit->outer_select();
 
89
    SELECT_LEX *upper= unit->outer_select();
118
90
    if (upper->parsing_place == IN_HAVING)
119
91
      upper->subquery_in_having= 1;
120
92
  }
121
93
  return;
122
94
}
123
95
 
124
 
Select_Lex *
 
96
st_select_lex *
125
97
Item_subselect::get_select_lex()
126
98
{
127
99
  return unit->first_select();
171
143
}
172
144
 
173
145
Item_subselect::trans_res
174
 
Item_subselect::select_transformer(JOIN *)
 
146
Item_subselect::select_transformer(JOIN *join __attribute__((unused)))
175
147
{
176
148
  return(RES_OK);
177
149
}
178
150
 
179
151
 
180
 
bool Item_subselect::fix_fields(Session *session_param, Item **ref)
 
152
bool Item_subselect::fix_fields(THD *thd_param, Item **ref)
181
153
{
182
 
  char const *save_where= session_param->where;
 
154
  char const *save_where= thd_param->where;
183
155
  uint8_t uncacheable;
184
156
  bool res;
185
157
 
186
158
  assert(fixed == 0);
187
 
  engine->set_session((session= session_param));
 
159
  engine->set_thd((thd= thd_param));
188
160
 
189
 
  if (check_stack_overrun(session, STACK_MIN_SIZE, (unsigned char*)&res))
 
161
  if (check_stack_overrun(thd, STACK_MIN_SIZE, (unsigned char*)&res))
190
162
    return true;
191
163
 
192
164
  res= engine->prepare();
217
189
      if (have_to_be_excluded)
218
190
        engine->exclude();
219
191
      substitution= 0;
220
 
      session->where= "checking transformed subquery";
 
192
      thd->where= "checking transformed subquery";
221
193
      if (!(*ref)->fixed)
222
 
        ret= (*ref)->fix_fields(session, ref);
223
 
      session->where= save_where;
 
194
        ret= (*ref)->fix_fields(thd, ref);
 
195
      thd->where= save_where;
224
196
      return ret;
225
197
    }
226
198
    // Is it one field subselect?
233
205
  }
234
206
  else
235
207
    goto err;
236
 
 
 
208
  
237
209
  if ((uncacheable= engine->uncacheable()))
238
210
  {
239
211
    const_item_cache= 0;
243
215
  fixed= 1;
244
216
 
245
217
err:
246
 
  session->where= save_where;
 
218
  thd->where= save_where;
247
219
  return res;
248
220
}
249
221
 
254
226
 
255
227
  if (walk_subquery)
256
228
  {
257
 
    for (Select_Lex *lex= unit->first_select(); lex; lex= lex->next_select())
 
229
    for (SELECT_LEX *lex= unit->first_select(); lex; lex= lex->next_select())
258
230
    {
259
231
      List_iterator<Item> li(lex->item_list);
260
232
      Item *item;
291
263
{
292
264
  int res;
293
265
 
294
 
  if (session->is_error())
 
266
  if (thd->is_error())
295
267
  /* Do not execute subselect in case of a fatal error */
296
268
    return 1;
297
269
 
371
343
  return const_item_cache;
372
344
}
373
345
 
374
 
Item *Item_subselect::get_tmp_table_item(Session *session_arg)
 
346
Item *Item_subselect::get_tmp_table_item(THD *thd_arg)
375
347
{
376
348
  if (!with_sum_func && !const_item())
377
349
    return new Item_field(result_field);
378
 
  return copy_or_same(session_arg);
 
350
  return copy_or_same(thd_arg);
379
351
}
380
352
 
381
353
void Item_subselect::update_used_tables()
397
369
}
398
370
 
399
371
 
400
 
Item_singlerow_subselect::Item_singlerow_subselect(Select_Lex *select_lex)
 
372
Item_singlerow_subselect::Item_singlerow_subselect(st_select_lex *select_lex)
401
373
  :Item_subselect(), value(0)
402
374
{
403
375
  init(select_lex, new select_singlerow_subselect(this));
406
378
  return;
407
379
}
408
380
 
409
 
Select_Lex *
 
381
st_select_lex *
410
382
Item_singlerow_subselect::invalidate_and_restore_select_lex()
411
383
{
412
 
  Select_Lex *result= get_select_lex();
 
384
  st_select_lex *result= get_select_lex();
413
385
 
414
386
  assert(result);
415
387
 
416
388
  /*
417
389
    This code restore the parse tree in it's state before the execution of
418
390
    Item_singlerow_subselect::Item_singlerow_subselect(),
419
 
    and in particular decouples this object from the Select_Lex,
420
 
    so that the Select_Lex can be used with a different flavor
 
391
    and in particular decouples this object from the SELECT_LEX,
 
392
    so that the SELECT_LEX can be used with a different flavor
421
393
    or Item_subselect instead, as part of query rewriting.
422
394
  */
423
395
  unit->item= NULL;
425
397
  return(result);
426
398
}
427
399
 
428
 
Item_maxmin_subselect::Item_maxmin_subselect(Session *session_param,
 
400
Item_maxmin_subselect::Item_maxmin_subselect(THD *thd_param,
429
401
                                             Item_subselect *parent,
430
 
                                             Select_Lex *select_lex,
 
402
                                             st_select_lex *select_lex,
431
403
                                             bool max_arg)
432
404
  :Item_singlerow_subselect(), was_values(true)
433
405
{
446
418
 
447
419
  /*
448
420
    this subquery always creates during preparation, so we can assign
449
 
    session here
 
421
    thd here
450
422
  */
451
 
  session= session_param;
 
423
  thd= thd_param;
452
424
 
453
425
  return;
454
426
}
501
473
  if (changed)
502
474
    return(RES_OK);
503
475
 
504
 
  Select_Lex *select_lex= join->select_lex;
505
 
 
 
476
  SELECT_LEX *select_lex= join->select_lex;
 
477
 
506
478
  if (!select_lex->master_unit()->is_union() &&
507
479
      !select_lex->table_list.elements &&
508
480
      select_lex->item_list.elements == 1 &&
521
493
  {
522
494
 
523
495
    have_to_be_excluded= 1;
524
 
    if (session->lex->describe)
 
496
    if (thd->lex->describe)
525
497
    {
526
498
      char warn_buff[DRIZZLE_ERRMSG_SIZE];
527
 
      snprintf(warn_buff, sizeof(warn_buff), ER(ER_SELECT_REDUCED), select_lex->select_number);
528
 
      push_warning(session, DRIZZLE_ERROR::WARN_LEVEL_NOTE,
 
499
      sprintf(warn_buff, ER(ER_SELECT_REDUCED), select_lex->select_number);
 
500
      push_warning(thd, DRIZZLE_ERROR::WARN_LEVEL_NOTE,
529
501
                   ER_SELECT_REDUCED, warn_buff);
530
502
    }
531
503
    substitution= select_lex->item_list.head();
551
523
  return engine->type();
552
524
}
553
525
 
554
 
/*
555
 
 Don't rely on the result type to calculate field type.
 
526
/* 
 
527
 Don't rely on the result type to calculate field type. 
556
528
 Ask the engine instead.
557
529
*/
558
530
enum_field_types Item_singlerow_subselect::field_type() const
568
540
  }
569
541
  else
570
542
  {
571
 
    if (!(row= (Item_cache**) memory::sql_alloc(sizeof(Item_cache*)*max_columns)))
 
543
    if (!(row= (Item_cache**) sql_alloc(sizeof(Item_cache*)*max_columns)))
572
544
      return;
573
545
    engine->fix_length_and_dec(row);
574
546
    value= *row;
688
660
}
689
661
 
690
662
 
691
 
Item_exists_subselect::Item_exists_subselect(Select_Lex *select_lex):
 
663
Item_exists_subselect::Item_exists_subselect(st_select_lex *select_lex):
692
664
  Item_subselect()
693
665
{
694
666
  bool val_bool();
708
680
}
709
681
 
710
682
 
711
 
bool Item_in_subselect::test_limit(Select_Lex_Unit *unit_arg)
 
683
bool Item_in_subselect::test_limit(st_select_lex_unit *unit_arg)
712
684
{
713
685
  if (unit_arg->fake_select_lex &&
714
686
      unit_arg->fake_select_lex->test_limit())
715
687
    return(1);
716
688
 
717
 
  Select_Lex *sl= unit_arg->first_select();
 
689
  SELECT_LEX *sl= unit_arg->first_select();
718
690
  for (; sl; sl= sl->next_select())
719
691
  {
720
692
    if (sl->test_limit())
724
696
}
725
697
 
726
698
Item_in_subselect::Item_in_subselect(Item * left_exp,
727
 
                                     Select_Lex *select_lex) :
728
 
  Item_exists_subselect(),
729
 
  left_expr(left_exp),
730
 
  left_expr_cache(NULL),
731
 
  first_execution(true),
732
 
  optimizer(NULL),
733
 
  pushed_cond_guards(NULL),
734
 
  sj_convert_priority(0),
735
 
  expr_join_nest(NULL),
736
 
  exec_method(NOT_TRANSFORMED),
737
 
  upper_item(NULL)
 
699
                                     st_select_lex *select_lex):
 
700
  Item_exists_subselect(), left_expr_cache(0), first_execution(true),
 
701
  optimizer(0), pushed_cond_guards(NULL), exec_method(NOT_TRANSFORMED),
 
702
  upper_item(0)
738
703
{
 
704
  left_expr= left_exp;
739
705
  init(select_lex, new select_exists_subselect(this));
740
706
  max_columns= UINT_MAX;
741
707
  maybe_null= 1;
748
714
 
749
715
Item_allany_subselect::Item_allany_subselect(Item * left_exp,
750
716
                                             chooser_compare_func_creator fc,
751
 
                                             Select_Lex *select_lex,
 
717
                                             st_select_lex *select_lex,
752
718
                                             bool all_arg)
753
719
  :Item_in_subselect(), func_creator(fc), all(all_arg)
754
720
{
906
872
  if (exec())
907
873
  {
908
874
    reset();
909
 
    /*
 
875
    /* 
910
876
      Must mark the IN predicate as NULL so as to make sure an enclosing NOT
911
 
      predicate will return false. See the comments in
 
877
      predicate will return false. See the comments in 
912
878
      subselect_uniquesubquery_engine::copy_ref_key for further details.
913
879
    */
914
880
    null_value= 1;
941
907
}
942
908
 
943
909
 
944
 
/*
 
910
/* 
945
911
  Rewrite a single-column IN/ALL/ANY subselect
946
912
 
947
913
  SYNOPSIS
951
917
 
952
918
  DESCRIPTION
953
919
    Rewrite a single-column subquery using rule-based approach. The subquery
954
 
 
 
920
    
955
921
       oe $cmp$ (SELECT ie FROM ... WHERE subq_where ... HAVING subq_having)
956
 
 
 
922
    
957
923
    First, try to convert the subquery to scalar-result subquery in one of
958
924
    the forms:
959
 
 
 
925
    
960
926
       - oe $cmp$ (SELECT MAX(...) )  // handled by Item_singlerow_subselect
961
927
       - oe $cmp$ <max>(SELECT ...)   // handled by Item_maxmin_subselect
962
 
 
 
928
   
963
929
    If that fails, the subquery will be handled with class Item_in_optimizer.
964
930
    There are two possibilites:
965
931
    - If the subquery execution method is materialization, then the subquery is
977
943
 
978
944
Item_subselect::trans_res
979
945
Item_in_subselect::single_value_transformer(JOIN *join,
980
 
                                            const Comp_creator *func)
 
946
                                            Comp_creator *func)
981
947
{
982
 
  Select_Lex *select_lex= join->select_lex;
 
948
  SELECT_LEX *select_lex= join->select_lex;
983
949
 
984
950
  /*
985
951
    Check that the right part of the subselect contains no more than one
1045
1011
        it.replace(item);
1046
1012
      }
1047
1013
 
1048
 
      save_allow_sum_func= session->lex->allow_sum_func;
1049
 
      session->lex->allow_sum_func|= 1 << session->lex->current_select->nest_level;
 
1014
      save_allow_sum_func= thd->lex->allow_sum_func;
 
1015
      thd->lex->allow_sum_func|= 1 << thd->lex->current_select->nest_level;
1050
1016
      /*
1051
1017
        Item_sum_(max|min) can't substitute other item => we can use 0 as
1052
1018
        reference, also Item_sum_(max|min) can't be fixed after creation, so
1053
1019
        we do not check item->fixed
1054
1020
      */
1055
 
      if (item->fix_fields(session, 0))
 
1021
      if (item->fix_fields(thd, 0))
1056
1022
        return(RES_ERROR);
1057
 
      session->lex->allow_sum_func= save_allow_sum_func;
 
1023
      thd->lex->allow_sum_func= save_allow_sum_func; 
1058
1024
      /* we added aggregate function => we have to change statistic */
1059
 
      count_field_types(select_lex, &join->tmp_table_param, join->all_fields,
 
1025
      count_field_types(select_lex, &join->tmp_table_param, join->all_fields, 
1060
1026
                        0);
1061
1027
 
1062
1028
      subs= new Item_singlerow_subselect(select_lex);
1064
1030
    else
1065
1031
    {
1066
1032
      Item_maxmin_subselect *item;
1067
 
      subs= item= new Item_maxmin_subselect(session, this, select_lex, func->l_op());
 
1033
      subs= item= new Item_maxmin_subselect(thd, this, select_lex, func->l_op());
1068
1034
      if (upper_item)
1069
1035
        upper_item->set_sub_test(item);
1070
1036
    }
1076
1042
  if (!substitution)
1077
1043
  {
1078
1044
    /* We're invoked for the 1st (or the only) SELECT in the subquery UNION */
1079
 
    Select_Lex_Unit *master_unit= select_lex->master_unit();
 
1045
    SELECT_LEX_UNIT *master_unit= select_lex->master_unit();
1080
1046
    substitution= optimizer;
1081
1047
 
1082
 
    Select_Lex *current= session->lex->current_select, *up;
 
1048
    SELECT_LEX *current= thd->lex->current_select, *up;
1083
1049
 
1084
 
    session->lex->current_select= up= current->return_after_parsing();
 
1050
    thd->lex->current_select= up= current->return_after_parsing();
1085
1051
    //optimizer never use Item **ref => we can pass 0 as parameter
1086
 
    if (!optimizer || optimizer->fix_left(session, 0))
 
1052
    if (!optimizer || optimizer->fix_left(thd, 0))
1087
1053
    {
1088
 
      session->lex->current_select= current;
 
1054
      thd->lex->current_select= current;
1089
1055
      return(RES_ERROR);
1090
1056
    }
1091
 
    session->lex->current_select= current;
 
1057
    thd->lex->current_select= current;
1092
1058
 
1093
1059
    /*
1094
1060
      As far as  Item_ref_in_optimizer do not substitute itself on fix_fields
1104
1070
 
1105
1071
  if (!abort_on_null && left_expr->maybe_null && !pushed_cond_guards)
1106
1072
  {
1107
 
    if (!(pushed_cond_guards= (bool*)join->session->alloc(sizeof(bool))))
 
1073
    if (!(pushed_cond_guards= (bool*)join->thd->alloc(sizeof(bool))))
1108
1074
      return(RES_ERROR);
1109
1075
    pushed_cond_guards[0]= true;
1110
1076
  }
1129
1095
 
1130
1096
  - If the subquery has aggregates, GROUP BY, or HAVING, convert to
1131
1097
 
1132
 
    SELECT ie FROM ...  HAVING subq_having AND
 
1098
    SELECT ie FROM ...  HAVING subq_having AND 
1133
1099
                               trigcond(oe $cmp$ ref_or_null_helper<ie>)
1134
 
 
 
1100
                                   
1135
1101
    the addition is wrapped into trigger only when we want to distinguish
1136
1102
    between NULL and false results.
1137
1103
 
1139
1105
    following:
1140
1106
 
1141
1107
    = If we don't need to distinguish between NULL and false subquery:
1142
 
 
 
1108
        
1143
1109
      SELECT 1 FROM ... WHERE (oe $cmp$ ie) AND subq_where
1144
1110
 
1145
1111
    = If we need to distinguish between those:
1158
1124
*/
1159
1125
 
1160
1126
Item_subselect::trans_res
1161
 
Item_in_subselect::single_value_in_to_exists_transformer(JOIN * join, const Comp_creator *func)
 
1127
Item_in_subselect::single_value_in_to_exists_transformer(JOIN * join, Comp_creator *func)
1162
1128
{
1163
 
  Select_Lex *select_lex= join->select_lex;
 
1129
  SELECT_LEX *select_lex= join->select_lex;
1164
1130
 
1165
1131
  select_lex->uncacheable|= UNCACHEABLE_DEPENDENT;
1166
1132
  if (join->having || select_lex->with_sum_func ||
1176
1142
                                                      this->full_name()));
1177
1143
    if (!abort_on_null && left_expr->maybe_null)
1178
1144
    {
1179
 
      /*
 
1145
      /* 
1180
1146
        We can encounter "NULL IN (SELECT ...)". Wrap the added condition
1181
1147
        within a trig_cond.
1182
1148
      */
1183
1149
      item= new Item_func_trig_cond(item, get_cond_guard(0));
1184
1150
    }
1185
 
 
 
1151
    
1186
1152
    /*
1187
1153
      AND and comparison functions can't be changed during fix_fields()
1188
1154
      we can assign select_lex->having here, and pass 0 as last
1196
1162
      we do not check join->having->fixed, because Item_and (from and_items)
1197
1163
      or comparison function (from func->create) can't be fixed after creation
1198
1164
    */
1199
 
    tmp= join->having->fix_fields(session, 0);
 
1165
    tmp= join->having->fix_fields(thd, 0);
1200
1166
    select_lex->having_fix_field= 0;
1201
1167
    if (tmp)
1202
1168
      return(RES_ERROR);
1214
1180
                                                   (int64_t) 1,
1215
1181
                                                   MY_INT64_NUM_DECIMAL_DIGITS));
1216
1182
      select_lex->ref_pointer_array[0]= select_lex->item_list.head();
1217
 
 
 
1183
       
1218
1184
      item= func->create(expr, item);
1219
1185
      if (!abort_on_null && orig_item->maybe_null)
1220
1186
      {
1238
1204
          and_items) or comparison function (from func->create) can't be
1239
1205
          fixed after creation
1240
1206
        */
1241
 
        tmp= join->having->fix_fields(session, 0);
 
1207
        tmp= join->having->fix_fields(thd, 0);
1242
1208
        select_lex->having_fix_field= 0;
1243
1209
        if (tmp)
1244
1210
          return(RES_ERROR);
1245
1211
        item= new Item_cond_or(item,
1246
1212
                               new Item_func_isnull(orig_item));
1247
1213
      }
1248
 
      /*
 
1214
      /* 
1249
1215
        If we may encounter NULL IN (SELECT ...) and care whether subquery
1250
1216
        result is NULL or false, wrap condition in a trig_cond.
1251
1217
      */
1255
1221
          return(RES_ERROR);
1256
1222
      }
1257
1223
      /*
1258
 
        TODO: figure out why the following is done here in
 
1224
        TODO: figure out why the following is done here in 
1259
1225
        single_value_transformer but there is no corresponding action in
1260
1226
        row_value_transformer?
1261
1227
      */
1272
1238
        we do not check join->conds->fixed, because Item_and can't be fixed
1273
1239
        after creation
1274
1240
      */
1275
 
      if (join->conds->fix_fields(session, 0))
 
1241
      if (join->conds->fix_fields(thd, 0))
1276
1242
        return(RES_ERROR);
1277
1243
    }
1278
1244
    else
1300
1266
        new_having->name= (char*)in_having_cond;
1301
1267
        select_lex->having= join->having= new_having;
1302
1268
        select_lex->having_fix_field= 1;
1303
 
 
 
1269
        
1304
1270
        /*
1305
1271
          we do not check join->having->fixed, because comparison function
1306
1272
          (from func->create) can't be fixed after creation
1307
1273
        */
1308
 
        tmp= join->having->fix_fields(session, 0);
 
1274
        tmp= join->having->fix_fields(thd, 0);
1309
1275
        select_lex->having_fix_field= 0;
1310
1276
        if (tmp)
1311
1277
          return(RES_ERROR);
1317
1283
        // fix_field of item will be done in time of substituting
1318
1284
        substitution= item;
1319
1285
        have_to_be_excluded= 1;
1320
 
        if (session->lex->describe)
 
1286
        if (thd->lex->describe)
1321
1287
        {
1322
1288
          char warn_buff[DRIZZLE_ERRMSG_SIZE];
1323
 
          snprintf(warn_buff, sizeof(warn_buff), ER(ER_SELECT_REDUCED), select_lex->select_number);
1324
 
          push_warning(session, DRIZZLE_ERROR::WARN_LEVEL_NOTE,
 
1289
          sprintf(warn_buff, ER(ER_SELECT_REDUCED), select_lex->select_number);
 
1290
          push_warning(thd, DRIZZLE_ERROR::WARN_LEVEL_NOTE,
1325
1291
                       ER_SELECT_REDUCED, warn_buff);
1326
1292
        }
1327
1293
        return(RES_REDUCE);
1336
1302
Item_subselect::trans_res
1337
1303
Item_in_subselect::row_value_transformer(JOIN *join)
1338
1304
{
1339
 
  Select_Lex *select_lex= join->select_lex;
 
1305
  SELECT_LEX *select_lex= join->select_lex;
1340
1306
  uint32_t cols_num= left_expr->cols();
1341
1307
 
1342
1308
  if (select_lex->item_list.elements != left_expr->cols())
1352
1318
  if (!substitution)
1353
1319
  {
1354
1320
    //first call for this unit
1355
 
    Select_Lex_Unit *master_unit= select_lex->master_unit();
 
1321
    SELECT_LEX_UNIT *master_unit= select_lex->master_unit();
1356
1322
    substitution= optimizer;
1357
1323
 
1358
 
    Select_Lex *current= session->lex->current_select, *up;
1359
 
    session->lex->current_select= up= current->return_after_parsing();
 
1324
    SELECT_LEX *current= thd->lex->current_select, *up;
 
1325
    thd->lex->current_select= up= current->return_after_parsing();
1360
1326
    //optimizer never use Item **ref => we can pass 0 as parameter
1361
 
    if (!optimizer || optimizer->fix_left(session, 0))
 
1327
    if (!optimizer || optimizer->fix_left(thd, 0))
1362
1328
    {
1363
 
      session->lex->current_select= current;
 
1329
      thd->lex->current_select= current;
1364
1330
      return(RES_ERROR);
1365
1331
    }
1366
1332
 
1367
1333
    // we will refer to upper level cache array => we have to save it in PS
1368
1334
    optimizer->keep_top_level_cache();
1369
1335
 
1370
 
    session->lex->current_select= current;
 
1336
    thd->lex->current_select= current;
1371
1337
    master_unit->uncacheable|= UNCACHEABLE_DEPENDENT;
1372
1338
 
1373
1339
    if (!abort_on_null && left_expr->maybe_null && !pushed_cond_guards)
1374
1340
    {
1375
 
      if (!(pushed_cond_guards= (bool*)join->session->alloc(sizeof(bool) *
 
1341
      if (!(pushed_cond_guards= (bool*)join->thd->alloc(sizeof(bool) *
1376
1342
                                                        left_expr->cols())))
1377
1343
        return(RES_ERROR);
1378
1344
      for (uint32_t i= 0; i < cols_num; i++)
1413
1379
Item_subselect::trans_res
1414
1380
Item_in_subselect::row_value_in_to_exists_transformer(JOIN * join)
1415
1381
{
1416
 
  Select_Lex *select_lex= join->select_lex;
 
1382
  SELECT_LEX *select_lex= join->select_lex;
1417
1383
  Item *having_item= 0;
1418
1384
  uint32_t cols_num= left_expr->cols();
1419
1385
  bool is_having_used= (join->having || select_lex->with_sum_func ||
1473
1439
          return(RES_ERROR);
1474
1440
      }
1475
1441
      having_item= and_items(having_item, col_item);
1476
 
 
1477
 
      Item *item_nnull_test=
 
1442
      
 
1443
      Item *item_nnull_test= 
1478
1444
         new Item_is_not_null_test(this,
1479
1445
                                   new Item_ref(&select_lex->context,
1480
1446
                                                select_lex->
1483
1449
                                                (char *)"<list ref>"));
1484
1450
      if (!abort_on_null && left_expr->element_index(i)->maybe_null)
1485
1451
      {
1486
 
        if (!(item_nnull_test=
 
1452
        if (!(item_nnull_test= 
1487
1453
              new Item_func_trig_cond(item_nnull_test, get_cond_guard(i))))
1488
1454
          return(RES_ERROR);
1489
1455
      }
1542
1508
        Item *having_col_item=
1543
1509
          new Item_is_not_null_test(this,
1544
1510
                                    new
1545
 
                                    Item_ref(&select_lex->context,
 
1511
                                    Item_ref(&select_lex->context, 
1546
1512
                                             select_lex->ref_pointer_array + i,
1547
1513
                                             (char *)"<no matter>",
1548
1514
                                             (char *)"<list ref>"));
1549
 
 
1550
 
 
 
1515
        
 
1516
        
1551
1517
        item_isnull= new
1552
1518
          Item_func_isnull(new
1553
1519
                           Item_direct_ref(&select_lex->context,
1557
1523
                                           (char *)"<list ref>")
1558
1524
                          );
1559
1525
        item= new Item_cond_or(item, item_isnull);
1560
 
        /*
 
1526
        /* 
1561
1527
          TODO: why we create the above for cases where the right part
1562
1528
                cant be NULL?
1563
1529
        */
1565
1531
        {
1566
1532
          if (!(item= new Item_func_trig_cond(item, get_cond_guard(i))))
1567
1533
            return(RES_ERROR);
1568
 
          if (!(having_col_item=
 
1534
          if (!(having_col_item= 
1569
1535
                  new Item_func_trig_cond(having_col_item, get_cond_guard(i))))
1570
1536
            return(RES_ERROR);
1571
1537
        }
1580
1546
    */
1581
1547
    select_lex->where= join->conds= and_items(join->conds, where_item);
1582
1548
    select_lex->where->top_level_item();
1583
 
    if (join->conds->fix_fields(session, 0))
 
1549
    if (join->conds->fix_fields(thd, 0))
1584
1550
      return(RES_ERROR);
1585
1551
  }
1586
1552
  if (having_item)
1596
1562
      argument (reference) to fix_fields()
1597
1563
    */
1598
1564
    select_lex->having_fix_field= 1;
1599
 
    res= join->having->fix_fields(session, 0);
 
1565
    res= join->having->fix_fields(thd, 0);
1600
1566
    select_lex->having_fix_field= 0;
1601
1567
    if (res)
1602
1568
    {
1611
1577
Item_subselect::trans_res
1612
1578
Item_in_subselect::select_transformer(JOIN *join)
1613
1579
{
1614
 
  return select_in_like_transformer(join, Eq_creator::instance());
 
1580
  return select_in_like_transformer(join, &eq_creator);
1615
1581
}
1616
1582
 
1617
1583
 
1637
1603
*/
1638
1604
 
1639
1605
Item_subselect::trans_res
1640
 
Item_in_subselect::select_in_like_transformer(JOIN *join, const Comp_creator *func)
 
1606
Item_in_subselect::select_in_like_transformer(JOIN *join, Comp_creator *func)
1641
1607
{
1642
 
  Select_Lex *current= session->lex->current_select, *up;
1643
 
  const char *save_where= session->where;
 
1608
  SELECT_LEX *current= thd->lex->current_select, *up;
 
1609
  const char *save_where= thd->where;
1644
1610
  Item_subselect::trans_res res= RES_ERROR;
1645
1611
  bool result;
1646
1612
 
1647
1613
  {
1648
1614
    /*
1649
1615
      IN/SOME/ALL/ANY subqueries aren't support LIMIT clause. Without it
1650
 
      ORDER BY clause becomes meaningless thus we drop it here.
 
1616
      order_st BY clause becomes meaningless thus we drop it here.
1651
1617
    */
1652
 
    Select_Lex *sl= current->master_unit()->first_select();
 
1618
    SELECT_LEX *sl= current->master_unit()->first_select();
1653
1619
    for (; sl; sl= sl->next_select())
1654
1620
    {
1655
1621
      if (sl->join)
1660
1626
  if (changed)
1661
1627
    return(RES_OK);
1662
1628
 
1663
 
  session->where= "IN/ALL/ANY subquery";
 
1629
  thd->where= "IN/ALL/ANY subquery";
1664
1630
 
1665
1631
  /*
1666
1632
    In some optimisation cases we will not need this Item_in_optimizer
1674
1640
      goto err;
1675
1641
  }
1676
1642
 
1677
 
  session->lex->current_select= up= current->return_after_parsing();
 
1643
  thd->lex->current_select= up= current->return_after_parsing();
1678
1644
  result= (!left_expr->fixed &&
1679
 
           left_expr->fix_fields(session, optimizer->arguments()));
 
1645
           left_expr->fix_fields(thd, optimizer->arguments()));
1680
1646
  /* fix_fields can change reference to left_expr, we need reassign it */
1681
1647
  left_expr= optimizer->arguments()[0];
1682
1648
 
1683
 
  session->lex->current_select= current;
 
1649
  thd->lex->current_select= current;
1684
1650
  if (result)
1685
1651
    goto err;
1686
1652
 
1703
1669
  else
1704
1670
  {
1705
1671
    /* we do not support row operation for ALL/ANY/SOME */
1706
 
    if (func != Eq_creator::instance())
 
1672
    if (func != &eq_creator)
1707
1673
    {
1708
1674
      my_error(ER_OPERAND_COLUMNS, MYF(0), 1);
1709
1675
      return(RES_ERROR);
1711
1677
    res= row_value_transformer(join);
1712
1678
  }
1713
1679
err:
1714
 
  session->where= save_where;
 
1680
  thd->where= save_where;
1715
1681
  return(res);
1716
1682
}
1717
1683
 
1729
1695
}
1730
1696
 
1731
1697
 
1732
 
bool Item_in_subselect::fix_fields(Session *session_arg, Item **ref)
 
1698
bool Item_in_subselect::fix_fields(THD *thd_arg, Item **ref)
1733
1699
{
1734
1700
  bool result = 0;
1735
1701
 
1736
1702
  if (exec_method == SEMI_JOIN)
1737
1703
    return !( (*ref)= new Item_int(1));
1738
1704
 
1739
 
  return result || Item_subselect::fix_fields(session_arg, ref);
 
1705
  return result || Item_subselect::fix_fields(thd_arg, ref);
1740
1706
}
1741
1707
 
1742
1708
 
1772
1738
  if (engine->engine_type() == subselect_engine::SINGLE_SELECT_ENGINE)
1773
1739
  {
1774
1740
    /* Create/initialize objects in permanent memory. */
1775
 
    subselect_single_select_engine *old_engine_ptr;
1776
 
 
1777
 
    old_engine_ptr= static_cast<subselect_single_select_engine *>(engine);
1778
 
 
1779
 
    if (!(new_engine= new subselect_hash_sj_engine(session, this,
1780
 
                                                   old_engine_ptr)) ||
 
1741
    subselect_single_select_engine *old_engine;
 
1742
 
 
1743
    old_engine= (subselect_single_select_engine*) engine;
 
1744
 
 
1745
    if (!(new_engine= new subselect_hash_sj_engine(thd, this,
 
1746
                                                   old_engine)) ||
1781
1747
        new_engine->init_permanent(unit->get_unit_column_types()))
1782
1748
    {
1783
 
      Item_subselect::trans_res new_trans_res;
 
1749
      Item_subselect::trans_res trans_res;
1784
1750
      /*
1785
1751
        If for some reason we cannot use materialization for this IN predicate,
1786
1752
        delete all materialization-related objects, and apply the IN=>EXISTS
1790
1756
      new_engine= NULL;
1791
1757
      exec_method= NOT_TRANSFORMED;
1792
1758
      if (left_expr->cols() == 1)
1793
 
        new_trans_res= single_value_in_to_exists_transformer(
1794
 
                           old_engine_ptr->join,
1795
 
                           Eq_creator::instance());
 
1759
        trans_res= single_value_in_to_exists_transformer(old_engine->join,
 
1760
                                                         &eq_creator);
1796
1761
      else
1797
 
        new_trans_res= row_value_in_to_exists_transformer(old_engine_ptr->join);
1798
 
      res= (new_trans_res != Item_subselect::RES_OK);
 
1762
        trans_res= row_value_in_to_exists_transformer(old_engine->join);
 
1763
      res= (trans_res != Item_subselect::RES_OK);
1799
1764
    }
1800
1765
    if (new_engine)
1801
1766
      engine= new_engine;
1803
1768
  else
1804
1769
  {
1805
1770
    assert(engine->engine_type() == subselect_engine::HASH_SJ_ENGINE);
1806
 
    new_engine= static_cast<subselect_hash_sj_engine *>(engine);
 
1771
    new_engine= (subselect_hash_sj_engine*) engine;
1807
1772
  }
1808
1773
 
1809
1774
  /* Initilizations done in runtime memory, repeated for each execution. */
1840
1805
 
1841
1806
bool Item_in_subselect::init_left_expr_cache()
1842
1807
{
1843
 
  JOIN *outer_join= NULL;
 
1808
  JOIN *outer_join;
 
1809
  Next_select_func end_select;
 
1810
  bool use_result_field= false;
1844
1811
 
1845
1812
  outer_join= unit->outer_select()->join;
1846
 
  if (! outer_join || ! outer_join->tables || ! outer_join->join_tab)
 
1813
  if (!outer_join || !outer_join->tables)
1847
1814
    return true;
 
1815
  /*
 
1816
    If we use end_[send | write]_group to handle complete rows of the outer
 
1817
    query, make the cache of the left IN operand use Item_field::result_field
 
1818
    instead of Item_field::field.  We need this because normally
 
1819
    Cached_item_field uses Item::field to fetch field data, while
 
1820
    copy_ref_key() that copies the left IN operand into a lookup key uses
 
1821
    Item::result_field. In the case end_[send | write]_group result_field is
 
1822
    one row behind field.
 
1823
  */
 
1824
  end_select= outer_join->join_tab[outer_join->tables-1].next_select;
 
1825
  if (end_select == end_send_group || end_select == end_write_group)
 
1826
    use_result_field= true;
1848
1827
 
1849
1828
  if (!(left_expr_cache= new List<Cached_item>))
1850
1829
    return true;
1851
1830
 
1852
1831
  for (uint32_t i= 0; i < left_expr->cols(); i++)
1853
1832
  {
1854
 
    Cached_item *cur_item_cache= new_Cached_item(session, left_expr->element_index(i));
 
1833
    Cached_item *cur_item_cache= new_Cached_item(thd,
 
1834
                                                 left_expr->element_index(i),
 
1835
                                                 use_result_field);
1855
1836
    if (!cur_item_cache || left_expr_cache->push_front(cur_item_cache))
1856
1837
      return true;
1857
1838
  }
1872
1853
  @retval false otherwise
1873
1854
*/
1874
1855
 
1875
 
bool Item_in_subselect::is_expensive_processor(unsigned char *)
 
1856
bool Item_in_subselect::is_expensive_processor(unsigned char *arg __attribute__((unused)))
1876
1857
{
1877
1858
  return exec_method == MATERIALIZATION;
1878
1859
}
1903
1884
}
1904
1885
 
1905
1886
 
1906
 
void subselect_engine::set_session(Session *session_arg)
 
1887
void subselect_engine::set_thd(THD *thd_arg)
1907
1888
{
1908
 
  session= session_arg;
 
1889
  thd= thd_arg;
1909
1890
  if (result)
1910
 
    result->set_session(session_arg);
 
1891
    result->set_thd(thd_arg);
1911
1892
}
1912
1893
 
1913
1894
 
1914
1895
subselect_single_select_engine::
1915
 
subselect_single_select_engine(Select_Lex *select,
 
1896
subselect_single_select_engine(st_select_lex *select,
1916
1897
                               select_result_interceptor *result_arg,
1917
1898
                               Item_subselect *item_arg)
1918
1899
  :subselect_engine(item_arg, result_arg),
1970
1951
void subselect_uniquesubquery_engine::cleanup()
1971
1952
{
1972
1953
  /* Tell handler we don't need the index anymore */
1973
 
  if (tab->table->cursor->inited)
1974
 
    tab->table->cursor->ha_index_end();
 
1954
  if (tab->table->file->inited)
 
1955
    tab->table->file->ha_index_end();
1975
1956
  return;
1976
1957
}
1977
1958
 
1978
1959
 
1979
 
subselect_union_engine::subselect_union_engine(Select_Lex_Unit *u,
 
1960
subselect_union_engine::subselect_union_engine(st_select_lex_unit *u,
1980
1961
                                               select_result_interceptor *result_arg,
1981
1962
                                               Item_subselect *item_arg)
1982
1963
  :subselect_engine(item_arg, result_arg)
2016
1997
{
2017
1998
  if (prepared)
2018
1999
    return 0;
2019
 
  join= new JOIN(session, select_lex->item_list,
 
2000
  join= new JOIN(thd, select_lex->item_list,
2020
2001
                 select_lex->options | SELECT_NO_UNLOCK, result);
2021
2002
  if (!join || !result)
2022
2003
    return 1; /* Fatal error is set already. */
2023
2004
  prepared= 1;
2024
 
  Select_Lex *save_select= session->lex->current_select;
2025
 
  session->lex->current_select= select_lex;
 
2005
  SELECT_LEX *save_select= thd->lex->current_select;
 
2006
  thd->lex->current_select= select_lex;
2026
2007
  if (join->prepare(&select_lex->ref_pointer_array,
2027
2008
                    (TableList*) select_lex->table_list.first,
2028
2009
                    select_lex->with_wild,
2032
2013
                    (order_st*) select_lex->order_list.first,
2033
2014
                    (order_st*) select_lex->group_list.first,
2034
2015
                    select_lex->having,
2035
 
                    select_lex, select_lex->master_unit()))
 
2016
                    (order_st*) 0, select_lex,
 
2017
                    select_lex->master_unit()))
2036
2018
    return 1;
2037
 
  session->lex->current_select= save_select;
 
2019
  thd->lex->current_select= save_select;
2038
2020
  return 0;
2039
2021
}
2040
2022
 
2041
2023
int subselect_union_engine::prepare()
2042
2024
{
2043
 
  return unit->prepare(session, result, (uint32_t)SELECT_NO_UNLOCK);
 
2025
  return unit->prepare(thd, result, SELECT_NO_UNLOCK);
2044
2026
}
2045
2027
 
2046
2028
int subselect_uniquesubquery_engine::prepare()
2067
2049
*/
2068
2050
 
2069
2051
bool subselect_single_select_engine::no_rows()
2070
 
{
 
2052
2071
2053
  return !item->assigned();
2072
2054
}
2073
2055
 
2074
2056
 
2075
 
/*
2076
 
 makes storage for the output values for the subquery and calcuates
 
2057
/* 
 
2058
 makes storage for the output values for the subquery and calcuates 
2077
2059
 their data and column types and their nullability.
2078
 
*/
 
2060
*/ 
2079
2061
void subselect_engine::set_row(List<Item> &item_list, Item_cache **row)
2080
2062
{
2081
2063
  Item *sel_item;
2124
2106
  }
2125
2107
}
2126
2108
 
2127
 
void subselect_uniquesubquery_engine::fix_length_and_dec(Item_cache **)
 
2109
void subselect_uniquesubquery_engine::fix_length_and_dec(Item_cache **row __attribute__((unused)))
2128
2110
{
2129
2111
  //this never should be called
2130
2112
  assert(0);
2131
2113
}
2132
2114
 
2133
 
int  init_read_record_seq(JoinTable *tab);
2134
 
int join_read_always_key_or_null(JoinTable *tab);
 
2115
int  init_read_record_seq(JOIN_TAB *tab);
 
2116
int join_read_always_key_or_null(JOIN_TAB *tab);
2135
2117
int join_read_next_same_or_null(READ_RECORD *info);
2136
2118
 
2137
2119
int subselect_single_select_engine::exec()
2138
2120
{
2139
 
  char const *save_where= session->where;
2140
 
  Select_Lex *save_select= session->lex->current_select;
2141
 
  session->lex->current_select= select_lex;
 
2121
  char const *save_where= thd->where;
 
2122
  SELECT_LEX *save_select= thd->lex->current_select;
 
2123
  thd->lex->current_select= select_lex;
2142
2124
  if (!join->optimized)
2143
2125
  {
2144
 
    Select_Lex_Unit *unit= select_lex->master_unit();
 
2126
    SELECT_LEX_UNIT *unit= select_lex->master_unit();
2145
2127
 
2146
2128
    unit->set_limit(unit->global_parameters);
 
2129
    if (join->flatten_subqueries())
 
2130
    {
 
2131
      thd->is_fatal_error= true;
 
2132
      return(1);
 
2133
    }
2147
2134
    if (join->optimize())
2148
2135
    {
2149
 
      session->where= save_where;
 
2136
      thd->where= save_where;
2150
2137
      executed= 1;
2151
 
      session->lex->current_select= save_select;
 
2138
      thd->lex->current_select= save_select;
2152
2139
      return(join->error ? join->error : 1);
2153
2140
    }
2154
 
    if (!select_lex->uncacheable && session->lex->describe &&
2155
 
        !(join->select_options & SELECT_DESCRIBE) &&
 
2141
    if (!select_lex->uncacheable && thd->lex->describe && 
 
2142
        !(join->select_options & SELECT_DESCRIBE) && 
2156
2143
        join->need_tmp && item->const_item())
2157
2144
    {
2158
2145
      /*
2164
2151
      select_lex->uncacheable|= UNCACHEABLE_EXPLAIN;
2165
2152
      select_lex->master_unit()->uncacheable|= UNCACHEABLE_EXPLAIN;
2166
2153
      if (join->init_save_join_tab())
2167
 
        return(1);
 
2154
        return(1);                        /* purecov: inspected */
2168
2155
    }
2169
2156
    if (item->engine_changed)
2170
2157
    {
2177
2164
  {
2178
2165
    if (join->reinit())
2179
2166
    {
2180
 
      session->where= save_where;
2181
 
      session->lex->current_select= save_select;
 
2167
      thd->where= save_where;
 
2168
      thd->lex->current_select= save_select;
2182
2169
      return(1);
2183
2170
    }
2184
2171
    item->reset();
2187
2174
  if (!executed)
2188
2175
  {
2189
2176
    item->reset_value_registration();
2190
 
    JoinTable *changed_tabs[MAX_TABLES];
2191
 
    JoinTable **last_changed_tab= changed_tabs;
 
2177
    JOIN_TAB *changed_tabs[MAX_TABLES];
 
2178
    JOIN_TAB **last_changed_tab= changed_tabs;
2192
2179
    if (item->have_guarded_conds())
2193
2180
    {
2194
2181
      /*
2199
2186
      */
2200
2187
      for (uint32_t i=join->const_tables ; i < join->tables ; i++)
2201
2188
      {
2202
 
        JoinTable *tab=join->join_tab+i;
 
2189
        JOIN_TAB *tab=join->join_tab+i;
2203
2190
        if (tab && tab->keyuse)
2204
2191
        {
2205
 
          for (uint32_t key_part= 0;
2206
 
               key_part < tab->ref.key_parts;
2207
 
               key_part++)
 
2192
          for (uint32_t i= 0; i < tab->ref.key_parts; i++)
2208
2193
          {
2209
 
            bool *cond_guard= tab->ref.cond_guards[key_part];
 
2194
            bool *cond_guard= tab->ref.cond_guards[i];
2210
2195
            if (cond_guard && !*cond_guard)
2211
2196
            {
2212
2197
              /* Change the access method to full table scan */
2214
2199
              tab->save_read_record= tab->read_record.read_record;
2215
2200
              tab->read_first_record= init_read_record_seq;
2216
2201
              tab->read_record.record= tab->table->record[0];
2217
 
              tab->read_record.session= join->session;
2218
 
              tab->read_record.ref_length= tab->table->cursor->ref_length;
 
2202
              tab->read_record.thd= join->thd;
 
2203
              tab->read_record.ref_length= tab->table->file->ref_length;
2219
2204
              *(last_changed_tab++)= tab;
2220
2205
              break;
2221
2206
            }
2223
2208
        }
2224
2209
      }
2225
2210
    }
2226
 
 
 
2211
    
2227
2212
    join->exec();
2228
2213
 
2229
2214
    /* Enable the optimizations back */
2230
 
    for (JoinTable **ptab= changed_tabs; ptab != last_changed_tab; ptab++)
 
2215
    for (JOIN_TAB **ptab= changed_tabs; ptab != last_changed_tab; ptab++)
2231
2216
    {
2232
 
      JoinTable *tab= *ptab;
 
2217
      JOIN_TAB *tab= *ptab;
2233
2218
      tab->read_record.record= 0;
2234
2219
      tab->read_record.ref_length= 0;
2235
 
      tab->read_first_record= tab->save_read_first_record;
 
2220
      tab->read_first_record= tab->save_read_first_record; 
2236
2221
      tab->read_record.read_record= tab->save_read_record;
2237
2222
    }
2238
2223
    executed= 1;
2239
 
    session->where= save_where;
2240
 
    session->lex->current_select= save_select;
2241
 
    return(join->error||session->is_fatal_error);
 
2224
    thd->where= save_where;
 
2225
    thd->lex->current_select= save_select;
 
2226
    return(join->error||thd->is_fatal_error);
2242
2227
  }
2243
 
  session->where= save_where;
2244
 
  session->lex->current_select= save_select;
 
2228
  thd->where= save_where;
 
2229
  thd->lex->current_select= save_select;
2245
2230
  return(0);
2246
2231
}
2247
2232
 
2248
2233
int subselect_union_engine::exec()
2249
2234
{
2250
 
  char const *save_where= session->where;
 
2235
  char const *save_where= thd->where;
2251
2236
  int res= unit->exec();
2252
 
  session->where= save_where;
 
2237
  thd->where= save_where;
2253
2238
  return res;
2254
2239
}
2255
2240
 
2256
2241
 
2257
2242
/*
2258
2243
  Search for at least one row satisfying select condition
2259
 
 
 
2244
 
2260
2245
  SYNOPSIS
2261
2246
    subselect_uniquesubquery_engine::scan_table()
2262
2247
 
2263
2248
  DESCRIPTION
2264
2249
    Scan the table using sequential access until we find at least one row
2265
2250
    satisfying select condition.
2266
 
 
 
2251
    
2267
2252
    The caller must set this->empty_result_set=false before calling this
2268
2253
    function. This function will set it to true if it finds a matching row.
2269
2254
 
2277
2262
  int error;
2278
2263
  Table *table= tab->table;
2279
2264
 
2280
 
  if (table->cursor->inited)
2281
 
    table->cursor->ha_index_end();
2282
 
 
2283
 
  table->cursor->ha_rnd_init(1);
2284
 
  table->cursor->extra_opt(HA_EXTRA_CACHE,
2285
 
                         current_session->variables.read_buff_size);
 
2265
  if (table->file->inited)
 
2266
    table->file->ha_index_end();
 
2267
 
 
2268
  table->file->ha_rnd_init(1);
 
2269
  table->file->extra_opt(HA_EXTRA_CACHE,
 
2270
                         current_thd->variables.read_buff_size);
2286
2271
  table->null_row= 0;
2287
2272
  for (;;)
2288
2273
  {
2289
 
    error=table->cursor->rnd_next(table->record[0]);
 
2274
    error=table->file->rnd_next(table->record[0]);
2290
2275
    if (error && error != HA_ERR_END_OF_FILE)
2291
2276
    {
2292
2277
      error= table->report_error(error);
2303
2288
    }
2304
2289
  }
2305
2290
 
2306
 
  table->cursor->ha_rnd_end();
 
2291
  table->file->ha_rnd_end();
2307
2292
  return(error != 0);
2308
2293
}
2309
2294
 
2352
2337
 
2353
2338
bool subselect_uniquesubquery_engine::copy_ref_key()
2354
2339
{
2355
 
  for (StoredKey **copy= tab->ref.key_copy ; *copy ; copy++)
 
2340
  for (store_key **copy= tab->ref.key_copy ; *copy ; copy++)
2356
2341
  {
2357
 
    StoredKey::store_key_result store_res= (*copy)->copy();
 
2342
    enum store_key::store_key_result store_res;
 
2343
    store_res= (*copy)->copy();
2358
2344
    tab->ref.key_err= store_res;
2359
2345
 
2360
2346
    /*
2382
2368
    }
2383
2369
 
2384
2370
    /*
2385
 
      Check if the error is equal to STORE_KEY_FATAL. This is not expressed
2386
 
      using the StoredKey::store_key_result enum because ref.key_err is a
2387
 
      boolean and we want to detect both true and STORE_KEY_FATAL from the
2388
 
      space of the union of the values of [true, false] and
2389
 
      StoredKey::store_key_result.
 
2371
      Check if the error is equal to STORE_KEY_FATAL. This is not expressed 
 
2372
      using the store_key::store_key_result enum because ref.key_err is a 
 
2373
      boolean and we want to detect both true and STORE_KEY_FATAL from the 
 
2374
      space of the union of the values of [true, false] and 
 
2375
      store_key::store_key_result.  
2390
2376
      TODO: fix the variable an return types.
2391
2377
    */
2392
 
    if (store_res == StoredKey::STORE_KEY_FATAL)
 
2378
    if (store_res == store_key::STORE_KEY_FATAL)
2393
2379
    {
2394
2380
      /*
2395
2381
       Error converting the left IN operand to the column type of the right
2396
 
       IN operand.
 
2382
       IN operand. 
2397
2383
      */
2398
2384
      tab->table->status= STATUS_NOT_FOUND;
2399
2385
      break;
2414
2400
    If some part of the lookup key is NULL, then we're evaluating
2415
2401
      NULL IN (SELECT ... )
2416
2402
    This is a special case, we don't need to search for NULL in the table,
2417
 
    instead, the result value is
 
2403
    instead, the result value is 
2418
2404
      - NULL  if select produces empty row set
2419
2405
      - false otherwise.
2420
2406
 
2421
2407
    In some cases (IN subselect is a top level item, i.e. abort_on_null==true)
2422
2408
    the caller doesn't distinguish between NULL and false result and we just
2423
 
    return false.
2424
 
    Otherwise we make a full table scan to see if there is at least one
 
2409
    return false. 
 
2410
    Otherwise we make a full table scan to see if there is at least one 
2425
2411
    matching row.
2426
 
 
 
2412
    
2427
2413
    The result of this function (info about whether a row was found) is
2428
2414
    stored in this->empty_result_set.
2429
2415
  NOTE
2430
 
 
 
2416
    
2431
2417
  RETURN
2432
2418
    false - ok
2433
2419
    true  - an error occured while scanning
2439
2425
  Table *table= tab->table;
2440
2426
  empty_result_set= true;
2441
2427
  table->status= 0;
2442
 
 
 
2428
 
2443
2429
  /* TODO: change to use of 'full_scan' here? */
2444
2430
  if (copy_ref_key())
2445
2431
    return(1);
2446
2432
  if (table->status)
2447
2433
  {
2448
 
    /*
2449
 
      We know that there will be no rows even if we scan.
 
2434
    /* 
 
2435
      We know that there will be no rows even if we scan. 
2450
2436
      Can be set in copy_ref_key.
2451
2437
    */
2452
2438
    ((Item_in_subselect *) item)->value= 0;
2455
2441
 
2456
2442
  if (null_keypart)
2457
2443
    return(scan_table());
2458
 
 
2459
 
  if (!table->cursor->inited)
2460
 
    table->cursor->ha_index_init(tab->ref.key, 0);
2461
 
  error= table->cursor->index_read_map(table->record[0],
 
2444
 
 
2445
  if (!table->file->inited)
 
2446
    table->file->ha_index_init(tab->ref.key, 0);
 
2447
  error= table->file->index_read_map(table->record[0],
2462
2448
                                     tab->ref.key_buff,
2463
2449
                                     make_prev_keypart_map(tab->ref.key_parts),
2464
2450
                                     HA_READ_KEY_EXACT);
2487
2473
 
2488
2474
  SYNOPSIS
2489
2475
    subselect_indexsubquery_engine:exec()
2490
 
      full_scan
 
2476
      full_scan 
2491
2477
 
2492
2478
  DESCRIPTION
2493
2479
    The engine is used to resolve subqueries in form
2494
2480
 
2495
 
      oe IN (SELECT key FROM tbl WHERE subq_where)
 
2481
      oe IN (SELECT key FROM tbl WHERE subq_where) 
2496
2482
 
2497
 
    The value of the predicate is calculated as follows:
 
2483
    The value of the predicate is calculated as follows: 
2498
2484
    1. If oe IS NULL, this is a special case, do a full table scan on
2499
 
       table tbl and search for row that satisfies subq_where. If such
 
2485
       table tbl and search for row that satisfies subq_where. If such 
2500
2486
       row is found, return NULL, otherwise return false.
2501
2487
    2. Make an index lookup via key=oe, search for a row that satisfies
2502
2488
       subq_where. If found, return true.
2503
 
    3. If check_null==true, make another lookup via key=NULL, search for a
 
2489
    3. If check_null==true, make another lookup via key=NULL, search for a 
2504
2490
       row that satisfies subq_where. If found, return NULL, otherwise
2505
2491
       return false.
2506
2492
 
2507
2493
  TODO
2508
2494
    The step #1 can be optimized further when the index has several key
2509
2495
    parts. Consider a subquery:
2510
 
 
 
2496
    
2511
2497
      (oe1, oe2) IN (SELECT keypart1, keypart2 FROM tbl WHERE subq_where)
2512
2498
 
2513
2499
    and suppose we need to evaluate it for {oe1, oe2}=={const1, NULL}.
2517
2503
      SELECT keypart1, keypart2 FROM tbl WHERE subq_where            (1)
2518
2504
 
2519
2505
    and checking if it has produced any matching rows, evaluate
2520
 
 
 
2506
    
2521
2507
      SELECT keypart2 FROM tbl WHERE subq_where AND keypart1=const1  (2)
2522
2508
 
2523
 
    If this query produces a row, the result is NULL (as we're evaluating
 
2509
    If this query produces a row, the result is NULL (as we're evaluating 
2524
2510
    "(const1, NULL) IN { (const1, X), ... }", which has a value of UNKNOWN,
2525
2511
    i.e. NULL).  If the query produces no rows, the result is false.
2526
2512
 
2558
2544
 
2559
2545
  if (table->status)
2560
2546
  {
2561
 
    /*
2562
 
      We know that there will be no rows even if we scan.
 
2547
    /* 
 
2548
      We know that there will be no rows even if we scan. 
2563
2549
      Can be set in copy_ref_key.
2564
2550
    */
2565
2551
    ((Item_in_subselect *) item)->value= 0;
2569
2555
  if (null_keypart)
2570
2556
    return(scan_table());
2571
2557
 
2572
 
  if (!table->cursor->inited)
2573
 
    table->cursor->ha_index_init(tab->ref.key, 1);
2574
 
  error= table->cursor->index_read_map(table->record[0],
 
2558
  if (!table->file->inited)
 
2559
    table->file->ha_index_init(tab->ref.key, 1);
 
2560
  error= table->file->index_read_map(table->record[0],
2575
2561
                                     tab->ref.key_buff,
2576
2562
                                     make_prev_keypart_map(tab->ref.key_parts),
2577
2563
                                     HA_READ_KEY_EXACT);
2595
2581
            ((Item_in_subselect *) item)->value= 1;
2596
2582
          break;
2597
2583
        }
2598
 
        error= table->cursor->index_next_same(table->record[0],
 
2584
        error= table->file->index_next_same(table->record[0],
2599
2585
                                            tab->ref.key_buff,
2600
2586
                                            tab->ref.key_length);
2601
2587
        if (error && error != HA_ERR_END_OF_FILE)
2691
2677
void subselect_single_select_engine::print(String *str,
2692
2678
                                           enum_query_type query_type)
2693
2679
{
2694
 
  select_lex->print(session, str, query_type);
 
2680
  select_lex->print(thd, str, query_type);
2695
2681
}
2696
2682
 
2697
2683
 
2833
2819
    true  error
2834
2820
*/
2835
2821
 
2836
 
bool subselect_uniquesubquery_engine::change_result(Item_subselect *,
2837
 
                                                    select_result_interceptor *)
 
2822
bool subselect_uniquesubquery_engine::change_result(Item_subselect *si __attribute__((unused)),
 
2823
                                                    select_result_interceptor *res __attribute__((unused)))
2838
2824
{
2839
2825
  assert(0);
2840
2826
  return true;
2881
2867
*/
2882
2868
bool subselect_union_engine::no_tables()
2883
2869
{
2884
 
  for (Select_Lex *sl= unit->first_select(); sl; sl= sl->next_select())
 
2870
  for (SELECT_LEX *sl= unit->first_select(); sl; sl= sl->next_select())
2885
2871
  {
2886
2872
    if (sl->table_list.elements)
2887
2873
      return false;
2920
2906
    temporary table has one hash index on all its columns.
2921
2907
  - Create a new result sink that sends the result stream of the subquery to
2922
2908
    the temporary table,
2923
 
  - Create and initialize a new JoinTable, and TABLE_REF objects to perform
 
2909
  - Create and initialize a new JOIN_TAB, and TABLE_REF objects to perform
2924
2910
    lookups into the indexed temporary table.
2925
2911
 
2926
2912
  @notice:
2951
2937
  if (!(tmp_result_sink= new select_union))
2952
2938
    return(true);
2953
2939
  if (tmp_result_sink->create_result_table(
2954
 
                         session, tmp_columns, true,
2955
 
                         session->options | TMP_TABLE_ALL_COLUMNS,
2956
 
                         "materialized subselect"))
 
2940
                         thd, tmp_columns, true,
 
2941
                         thd->options | TMP_TABLE_ALL_COLUMNS,
 
2942
                         "materialized subselect", true))
2957
2943
    return(true);
2958
2944
 
2959
2945
  tmp_table= tmp_result_sink->table;
2969
2955
  */
2970
2956
  if (tmp_table->s->keys == 0)
2971
2957
  {
2972
 
    assert(tmp_table->s->db_type() == myisam_engine);
 
2958
    assert(tmp_table->s->db_type() == myisam_hton);
2973
2959
    assert(
2974
2960
      tmp_table->s->uniques ||
2975
 
      tmp_table->key_info->key_length >= tmp_table->cursor->getEngine()->max_key_length() ||
2976
 
      tmp_table->key_info->key_parts > tmp_table->cursor->getEngine()->max_key_parts());
2977
 
    tmp_table->free_tmp_table(session);
 
2961
      tmp_table->key_info->key_length >= tmp_table->file->max_key_length() ||
 
2962
      tmp_table->key_info->key_parts > tmp_table->file->max_key_parts());
 
2963
    tmp_table->free_tmp_table(thd);
2978
2964
    delete result;
2979
2965
    result= NULL;
2980
2966
    return(true);
2991
2977
  /* 2. Create/initialize execution related objects. */
2992
2978
 
2993
2979
  /*
2994
 
    Create and initialize the JoinTable that represents an index lookup
 
2980
    Create and initialize the JOIN_TAB that represents an index lookup
2995
2981
    plan operator into the materialized subquery result. Notice that:
2996
 
    - this JoinTable has no corresponding JOIN (and doesn't need one), and
 
2982
    - this JOIN_TAB has no corresponding JOIN (and doesn't need one), and
2997
2983
    - here we initialize only those members that are used by
2998
2984
      subselect_uniquesubquery_engine, so these objects are incomplete.
2999
 
  */
3000
 
  if (!(tab= (JoinTable*) session->alloc(sizeof(JoinTable))))
 
2985
  */ 
 
2986
  if (!(tab= (JOIN_TAB*) thd->alloc(sizeof(JOIN_TAB))))
3001
2987
    return(true);
3002
2988
  tab->table= tmp_table;
3003
2989
  tab->ref.key= 0; /* The only temp table index. */
3004
2990
  tab->ref.key_length= tmp_key->key_length;
3005
2991
  if (!(tab->ref.key_buff=
3006
 
        (unsigned char*) session->calloc(ALIGN_SIZE(tmp_key->key_length) * 2)) ||
 
2992
        (unsigned char*) thd->calloc(ALIGN_SIZE(tmp_key->key_length) * 2)) ||
3007
2993
      !(tab->ref.key_copy=
3008
 
        (StoredKey**) session->alloc((sizeof(StoredKey*) *
 
2994
        (store_key**) thd->alloc((sizeof(store_key*) *
3009
2995
                                  (tmp_key_parts + 1)))) ||
3010
2996
      !(tab->ref.items=
3011
 
        (Item**) session->alloc(sizeof(Item*) * tmp_key_parts)))
 
2997
        (Item**) thd->alloc(sizeof(Item*) * tmp_key_parts)))
3012
2998
    return(true);
3013
2999
 
3014
3000
  KEY_PART_INFO *cur_key_part= tmp_key->key_part;
3015
 
  StoredKey **ref_key= tab->ref.key_copy;
 
3001
  store_key **ref_key= tab->ref.key_copy;
3016
3002
  unsigned char *cur_ref_buff= tab->ref.key_buff;
3017
 
 
 
3003
  
3018
3004
  for (uint32_t i= 0; i < tmp_key_parts; i++, cur_key_part++, ref_key++)
3019
3005
  {
3020
3006
    tab->ref.items[i]= item_in->left_expr->element_index(i);
3021
3007
    int null_count= test(cur_key_part->field->real_maybe_null());
3022
 
    *ref_key= new store_key_item(session, cur_key_part->field,
 
3008
    *ref_key= new store_key_item(thd, cur_key_part->field,
3023
3009
                                 /* TODO:
3024
3010
                                    the NULL byte is taken into account in
3025
3011
                                    cur_key_part->store_length, so instead of
3065
3051
{
3066
3052
  delete result;
3067
3053
  if (tab)
3068
 
    tab->table->free_tmp_table(session);
 
3054
    tab->table->free_tmp_table(thd);
3069
3055
}
3070
3056
 
3071
3057
 
3107
3093
  if (!is_materialized)
3108
3094
  {
3109
3095
    int res= 0;
3110
 
    Select_Lex *save_select= session->lex->current_select;
3111
 
    session->lex->current_select= materialize_engine->select_lex;
 
3096
    SELECT_LEX *save_select= thd->lex->current_select;
 
3097
    thd->lex->current_select= materialize_engine->select_lex;
3112
3098
    if ((res= materialize_join->optimize()))
3113
3099
      goto err;
3114
3100
    materialize_join->exec();
3115
 
    if ((res= test(materialize_join->error || session->is_fatal_error)))
 
3101
    if ((res= test(materialize_join->error || thd->is_fatal_error)))
3116
3102
      goto err;
3117
3103
 
3118
3104
    /*
3131
3117
      statistics, then we test if the temporary table for the query result is
3132
3118
      empty.
3133
3119
    */
3134
 
    tab->table->cursor->info(HA_STATUS_VARIABLE);
3135
 
    if (!tab->table->cursor->stats.records)
 
3120
    tab->table->file->info(HA_STATUS_VARIABLE);
 
3121
    if (!tab->table->file->stats.records)
3136
3122
    {
3137
3123
      empty_result_set= true;
3138
3124
      item_in->value= false;
3145
3131
      tmp_param= NULL;
3146
3132
 
3147
3133
err:
3148
 
    session->lex->current_select= save_select;
 
3134
    thd->lex->current_select= save_select;
3149
3135
    if (res)
3150
3136
      return(res);
3151
3137
  }
3173
3159
           "<the access method for lookups is not yet created>"
3174
3160
         ));
3175
3161
}
3176
 
 
3177
 
} /* namespace drizzled */