~drizzle-trunk/drizzle/development

« back to all changes in this revision

Viewing changes to drizzled/join.cc

  • Committer: Monty Taylor
  • Date: 2010-10-26 17:38:18 UTC
  • mto: (1880.1.1 build)
  • mto: This revision was merged to the branch mainline in revision 1881.
  • Revision ID: mordred@inaugust.com-20101026173818-1yol32mb18o66mmu
Turned some plugins off of load_by_default so we can package them easier.

Show diffs side-by-side

added added

removed removed

Lines of Context:
71
71
 
72
72
/** Declarations of static functions used in this source file. */
73
73
static bool make_group_fields(Join *main_join, Join *curr_join);
74
 
static void calc_group_buffer(Join *join, Order *group);
75
 
static bool alloc_group_fields(Join *join, Order *group);
 
74
static void calc_group_buffer(Join *join,order_st *group);
 
75
static bool alloc_group_fields(Join *join,order_st *group);
76
76
static uint32_t cache_record_length(Join *join, uint32_t index);
77
77
static double prev_record_reads(Join *join, uint32_t idx, table_map found_ref);
78
78
static bool get_best_combination(Join *join);
102
102
static bool make_join_select(Join *join, optimizer::SqlSelect *select,COND *item);
103
103
static bool make_join_readinfo(Join *join);
104
104
static void update_depend_map(Join *join);
105
 
static void update_depend_map(Join *join, Order *order);
106
 
static Order *remove_constants(Join *join,Order *first_order,COND *cond, bool change_list, bool *simple_order);
 
105
static void update_depend_map(Join *join, order_st *order);
 
106
static order_st *remove_constants(Join *join,order_st *first_order,COND *cond, bool change_list, bool *simple_order);
107
107
static int return_zero_rows(Join *join,
108
108
                            select_result *res,
109
109
                            TableList *tables,
121
121
                               List<Item> &fields,
122
122
                               List<Item> &all_fields,
123
123
                               COND **conds,
124
 
                               Order *order,
125
 
                               Order *group,
 
124
                               order_st *order,
 
125
                               order_st *group,
126
126
                               bool *hidden_group_fields);
127
127
static bool make_join_statistics(Join *join, TableList *leaves, COND *conds, DYNAMIC_ARRAY *keyuse);
128
128
static uint32_t build_bitmap_for_nested_joins(List<TableList> *join_list, uint32_t first_unused);
129
 
static Table *get_sort_by_table(Order *a, Order *b,TableList *tables);
 
129
static Table *get_sort_by_table(order_st *a,order_st *b,TableList *tables);
130
130
static void reset_nj_counters(List<TableList> *join_list);
131
 
static bool test_if_subpart(Order *a,Order *b);
 
131
static bool test_if_subpart(order_st *a,order_st *b);
132
132
static void restore_prev_nj_state(JoinTable *last);
133
133
static bool add_ref_to_table_cond(Session *session, JoinTable *join_tab);
134
134
static void free_blobs(Field **ptr); /* Rename this method...conflicts with another in global namespace... */
150
150
                  uint32_t wild_num,
151
151
                  COND *conds_init,
152
152
                  uint32_t og_num,
153
 
                  Order *order_init,
154
 
                  Order *group_init,
 
153
                  order_st *order_init,
 
154
                  order_st *group_init,
155
155
                  Item *having_init,
156
156
                  Select_Lex *select_lex_arg,
157
157
                  Select_Lex_Unit *unit_arg)
192
192
  for (table_ptr= select_lex->leaf_tables;
193
193
       table_ptr;
194
194
       table_ptr= table_ptr->next_leaf)
195
 
  {
196
195
    tables++;
197
 
  }
198
 
 
199
196
 
200
197
  if (setup_wild(session, fields_list, &all_fields, wild_num) ||
201
198
      select_lex->setup_ref_array(session, og_num) ||
291
288
 
292
289
  if (order)
293
290
  {
294
 
    Order *ord;
 
291
    order_st *ord;
295
292
    for (ord= order; ord; ord= ord->next)
296
293
    {
297
294
      Item *item= *ord->item;
336
333
  {
337
334
    /* Caclulate the number of groups */
338
335
    send_group_parts= 0;
339
 
    for (Order *group_tmp= group_list ; group_tmp ; group_tmp= group_tmp->next)
 
336
    for (order_st *group_tmp= group_list ; group_tmp ; group_tmp= group_tmp->next)
340
337
      send_group_parts++;
341
338
  }
342
339
 
594
591
    return 1;
595
592
  }
596
593
  if (const_tables && !(select_options & SELECT_NO_UNLOCK))
597
 
    session->unlockSomeTables(table, const_tables);
 
594
    mysql_unlock_some_tables(session, table, const_tables);
598
595
  if (!conds && outer_join)
599
596
  {
600
597
    /* Handle the case where we have an OUTER JOIN without a WHERE */
656
653
 
657
654
  /* Optimize distinct away if possible */
658
655
  {
659
 
    Order *org_order= order;
 
656
    order_st *org_order= order;
660
657
    order= remove_constants(this, order,conds,1, &simple_order);
661
658
    if (session->is_error())
662
659
    {
790
787
  }
791
788
  simple_group= 0;
792
789
  {
793
 
    Order *old_group_list;
 
790
    order_st *old_group_list;
794
791
    group_list= remove_constants(this, (old_group_list= group_list), conds,
795
792
                                 rollup.state == ROLLUP::STATE_NONE,
796
793
                                 &simple_group);
940
937
        Force using of tmp table if sorting by a SP or UDF function due to
941
938
        their expensive and probably non-deterministic nature.
942
939
      */
943
 
      for (Order *tmp_order= order; tmp_order ; tmp_order=tmp_order->next)
 
940
      for (order_st *tmp_order= order; tmp_order ; tmp_order=tmp_order->next)
944
941
      {
945
942
        Item *item= *tmp_order->item;
946
943
        if (item->is_expensive())
984
981
 
985
982
    tmp_table_param.hidden_field_count= (all_fields.elements -
986
983
           fields_list.elements);
987
 
    Order *tmp_group= ((!simple_group &&
 
984
    order_st *tmp_group= ((!simple_group && 
988
985
                           ! (test_flags.test(TEST_NO_KEY_GROUP))) ? group_list :
989
 
                                                                     (Order*) 0);
 
986
                                                                     (order_st*) 0);
990
987
    /*
991
988
      Pushing LIMIT to the temporary table creation is not applicable
992
989
      when there is ORDER BY or GROUP BY or there is no GROUP BY, but
1433
1430
              exec_tmp_table2= create_tmp_table(session,
1434
1431
                                                &curr_join->tmp_table_param,
1435
1432
                                                *curr_all_fields,
1436
 
                                                (Order*) 0,
 
1433
                                                (order_st*) 0,
1437
1434
                                                curr_join->select_distinct &&
1438
1435
                                                !curr_join->group_list,
1439
1436
                                                1, curr_join->select_options,
1791
1788
    is called after all rows are sent, but before EOF packet is sent.
1792
1789
 
1793
1790
    For a simple SELECT with no subqueries this function performs a full
1794
 
    cleanup of the Join and calls unlockReadTables to free used base
 
1791
    cleanup of the Join and calls mysql_unlock_read_tables to free used base
1795
1792
    tables.
1796
1793
 
1797
1794
    If a Join is executed for a subquery or if it has a subquery, we can't
1863
1860
      TODO: unlock tables even if the join isn't top level select in the
1864
1861
      tree.
1865
1862
    */
1866
 
    session->unlockReadTables(lock);           // Don't free join->lock
 
1863
    mysql_unlock_read_tables(session, lock);           // Don't free join->lock
1867
1864
    lock= 0;
1868
1865
  }
1869
1866
 
1993
1990
    */
1994
1991
    if (order)
1995
1992
    {
1996
 
      Order *ord;
 
1993
      order_st *ord;
1997
1994
      for (ord= order; ord; ord= ord->next)
1998
1995
        group_parts++;
1999
1996
    }
2103
2100
  Item *item;
2104
2101
  while ((item= it++))
2105
2102
  {
2106
 
    Order *group_tmp;
 
2103
    order_st *group_tmp;
2107
2104
    bool found_in_group= 0;
2108
2105
 
2109
2106
    for (group_tmp= group_list; group_tmp; group_tmp= group_tmp->next)
2132
2129
            return 1;
2133
2130
          new_item->fix_fields(session, (Item **) 0);
2134
2131
          session->change_item_tree(it.ref(), new_item);
2135
 
          for (Order *tmp= group_tmp; tmp; tmp= tmp->next)
 
2132
          for (order_st *tmp= group_tmp; tmp; tmp= tmp->next)
2136
2133
          {
2137
2134
            if (*tmp->item == item)
2138
2135
              session->change_item_tree(tmp->item, new_item);
2207
2204
    Item *item;
2208
2205
    List_iterator<Item> new_it(rollup.fields[pos]);
2209
2206
    Item **ref_array_start= rollup.ref_pointer_arrays[pos];
2210
 
    Order *start_group;
 
2207
    order_st *start_group;
2211
2208
 
2212
2209
    /* Point to first hidden field */
2213
2210
    Item **ref_array= ref_array_start + fields_arg.elements-1;
2249
2246
      else
2250
2247
      {
2251
2248
        /* Check if this is something that is part of this group by */
2252
 
        Order *group_tmp;
 
2249
        order_st *group_tmp;
2253
2250
        for (group_tmp= start_group, i= pos ;
2254
2251
                  group_tmp ; group_tmp= group_tmp->next, i++)
2255
2252
        {
2465
2462
    return NESTED_LOOP_ERROR;
2466
2463
  if (error < 0)
2467
2464
    return NESTED_LOOP_NO_MORE_ROWS;
2468
 
  if (join->session->getKilled())                       // Aborted by user
 
2465
  if (join->session->killed)                    // Aborted by user
2469
2466
  {
2470
2467
    join->session->send_kill_message();
2471
2468
    return NESTED_LOOP_KILLED;
2677
2674
  info= &join_tab->read_record;
2678
2675
  do
2679
2676
  {
2680
 
    if (join->session->getKilled())
 
2677
    if (join->session->killed)
2681
2678
    {
2682
2679
      join->session->send_kill_message();
2683
2680
      return NESTED_LOOP_KILLED;
2809
2806
{
2810
2807
  Table *table= join->tmp_table;
2811
2808
 
2812
 
  if (join->session->getKilled())                       // Aborted by user
 
2809
  if (join->session->killed)                    // Aborted by user
2813
2810
  {
2814
2811
    join->session->send_kill_message();
2815
2812
    return NESTED_LOOP_KILLED;
2817
2814
  if (!end_of_records)
2818
2815
  {
2819
2816
    copy_fields(&join->tmp_table_param);
2820
 
    if (copy_funcs(join->tmp_table_param.items_to_copy, join->session))
2821
 
      return NESTED_LOOP_ERROR;
 
2817
    copy_funcs(join->tmp_table_param.items_to_copy);
2822
2818
    if (!join->having || join->having->val_int())
2823
2819
    {
2824
2820
      int error;
2851
2847
enum_nested_loop_state end_update(Join *join, JoinTable *, bool end_of_records)
2852
2848
{
2853
2849
  Table *table= join->tmp_table;
2854
 
  Order *group;
 
2850
  order_st *group;
2855
2851
  int   error;
2856
2852
 
2857
2853
  if (end_of_records)
2858
2854
    return NESTED_LOOP_OK;
2859
 
  if (join->session->getKilled())                       // Aborted by user
 
2855
  if (join->session->killed)                    // Aborted by user
2860
2856
  {
2861
2857
    join->session->send_kill_message();
2862
2858
    return NESTED_LOOP_KILLED;
2903
2899
      memcpy(table->getInsertRecord()+key_part->offset, group->buff, 1);
2904
2900
  }
2905
2901
  init_tmptable_sum_functions(join->sum_funcs);
2906
 
  if (copy_funcs(join->tmp_table_param.items_to_copy, join->session))
2907
 
    return NESTED_LOOP_ERROR;
 
2902
  copy_funcs(join->tmp_table_param.items_to_copy);
2908
2903
  if ((error=table->cursor->insertRecord(table->getInsertRecord())))
2909
2904
  {
2910
2905
    my_error(ER_USE_SQL_BIG_RESULT, MYF(0));
2922
2917
 
2923
2918
  if (end_of_records)
2924
2919
    return NESTED_LOOP_OK;
2925
 
  if (join->session->getKilled())                       // Aborted by user
 
2920
  if (join->session->killed)                    // Aborted by user
2926
2921
  {
2927
2922
    join->session->send_kill_message();
2928
2923
    return NESTED_LOOP_KILLED;
2930
2925
 
2931
2926
  init_tmptable_sum_functions(join->sum_funcs);
2932
2927
  copy_fields(&join->tmp_table_param);          // Groups are copied twice.
2933
 
  if (copy_funcs(join->tmp_table_param.items_to_copy, join->session))
2934
 
    return NESTED_LOOP_ERROR;
 
2928
  copy_funcs(join->tmp_table_param.items_to_copy);
2935
2929
 
2936
2930
  if (!(error= table->cursor->insertRecord(table->getInsertRecord())))
2937
2931
    join->send_records++;                       // New group
2990
2984
/**
2991
2985
  calc how big buffer we need for comparing group entries.
2992
2986
*/
2993
 
static void calc_group_buffer(Join *join, Order *group)
 
2987
static void calc_group_buffer(Join *join,order_st *group)
2994
2988
{
2995
2989
  uint32_t key_length=0, parts=0, null_parts=0;
2996
2990
 
3016
3010
      case REAL_RESULT:
3017
3011
        key_length+= sizeof(double);
3018
3012
        break;
3019
 
 
3020
3013
      case INT_RESULT:
3021
3014
        key_length+= sizeof(int64_t);
3022
3015
        break;
3023
 
 
3024
3016
      case DECIMAL_RESULT:
3025
3017
        key_length+= my_decimal_get_binary_size(group_item->max_length -
3026
3018
                                                (group_item->decimals ? 1 : 0),
3027
3019
                                                group_item->decimals);
3028
3020
        break;
3029
 
 
3030
3021
      case STRING_RESULT:
3031
 
        {
3032
 
          enum enum_field_types type= group_item->field_type();
 
3022
      {
 
3023
        enum enum_field_types type= group_item->field_type();
 
3024
        /*
 
3025
          As items represented as DATE/TIME fields in the group buffer
 
3026
          have STRING_RESULT result type, we increase the length
 
3027
          by 8 as maximum pack length of such fields.
 
3028
        */
 
3029
        if (type == DRIZZLE_TYPE_DATE ||
 
3030
            type == DRIZZLE_TYPE_DATETIME ||
 
3031
            type == DRIZZLE_TYPE_TIMESTAMP)
 
3032
        {
 
3033
          key_length+= 8;
 
3034
        }
 
3035
        else
 
3036
        {
3033
3037
          /*
3034
 
            As items represented as DATE/TIME fields in the group buffer
3035
 
            have STRING_RESULT result type, we increase the length
3036
 
            by 8 as maximum pack length of such fields.
 
3038
            Group strings are taken as varstrings and require an length field.
 
3039
            A field is not yet created by create_tmp_field()
 
3040
            and the sizes should match up.
3037
3041
          */
3038
 
          if (type == DRIZZLE_TYPE_DATE ||
3039
 
              type == DRIZZLE_TYPE_DATETIME ||
3040
 
              type == DRIZZLE_TYPE_TIMESTAMP)
3041
 
          {
3042
 
            key_length+= 8;
3043
 
          }
3044
 
          else
3045
 
          {
3046
 
            /*
3047
 
              Group strings are taken as varstrings and require an length field.
3048
 
              A field is not yet created by create_tmp_field()
3049
 
              and the sizes should match up.
3050
 
            */
3051
 
            key_length+= group_item->max_length + HA_KEY_BLOB_LENGTH;
3052
 
          }
3053
 
          break;
 
3042
          key_length+= group_item->max_length + HA_KEY_BLOB_LENGTH;
3054
3043
        }
3055
 
 
3056
 
      case ROW_RESULT:
 
3044
        break;
 
3045
      }
 
3046
      default:
3057
3047
        /* This case should never be choosen */
3058
3048
        assert(0);
3059
3049
        my_error(ER_OUT_OF_RESOURCES, MYF(ME_FATALERROR));
3060
3050
      }
3061
3051
    }
3062
 
 
3063
3052
    parts++;
3064
 
 
3065
3053
    if (group_item->maybe_null)
3066
3054
      null_parts++;
3067
3055
  }
3068
 
 
3069
3056
  join->tmp_table_param.group_length=key_length+null_parts;
3070
3057
  join->tmp_table_param.group_parts=parts;
3071
3058
  join->tmp_table_param.group_null_parts=null_parts;
3076
3063
 
3077
3064
  Groups are saved in reverse order for easyer check loop.
3078
3065
*/
3079
 
static bool alloc_group_fields(Join *join, Order *group)
 
3066
static bool alloc_group_fields(Join *join,order_st *group)
3080
3067
{
3081
3068
  if (group)
3082
3069
  {
4195
4182
                                             uint32_t prune_level)
4196
4183
{
4197
4184
  Session *session= join->session;
4198
 
  if (session->getKilled())  // Abort
 
4185
  if (session->killed)  // Abort
4199
4186
    return(true);
4200
4187
 
4201
4188
  /*
4957
4944
}
4958
4945
 
4959
4946
/** Update the dependency map for the sort order. */
4960
 
static void update_depend_map(Join *join, Order *order)
 
4947
static void update_depend_map(Join *join, order_st *order)
4961
4948
{
4962
4949
  for (; order ; order=order->next)
4963
4950
  {
4995
4982
  @return
4996
4983
    Returns new sort order
4997
4984
*/
4998
 
static Order *remove_constants(Join *join,Order *first_order, COND *cond, bool change_list, bool *simple_order)
 
4985
static order_st *remove_constants(Join *join,order_st *first_order, COND *cond, bool change_list, bool *simple_order)
4999
4986
{
5000
4987
  if (join->tables == join->const_tables)
5001
4988
    return change_list ? 0 : first_order;               // No need to sort
5002
4989
 
5003
 
  Order *order,**prev_ptr;
 
4990
  order_st *order,**prev_ptr;
5004
4991
  table_map first_table= join->join_tab[join->const_tables].table->map;
5005
4992
  table_map not_const_tables= ~join->const_table_map;
5006
4993
  table_map ref;
5441
5428
                               List<Item> &fields,
5442
5429
                               List<Item> &all_fields,
5443
5430
                               COND **conds,
5444
 
                               Order *order,
5445
 
                               Order *group,
 
5431
                               order_st *order,
 
5432
                               order_st *group,
5446
5433
                               bool *hidden_group_fields)
5447
5434
{
5448
5435
  int res;
5881
5868
  if (join->const_tables != join->tables)
5882
5869
  {
5883
5870
    optimize_keyuse(join, keyuse_array);
5884
 
    // @note c_str() is not likely to be valid here if dtrace expects it to
5885
 
    // exist for any period of time.
5886
 
    DRIZZLE_QUERY_OPT_CHOOSE_PLAN_START(join->session->getQueryString()->c_str(), join->session->thread_id);
 
5871
    DRIZZLE_QUERY_OPT_CHOOSE_PLAN_START(join->session->query.c_str(), join->session->thread_id);
5887
5872
    bool res= choose_plan(join, all_table_map & ~join->const_table_map);
5888
5873
    DRIZZLE_QUERY_OPT_CHOOSE_PLAN_DONE(res ? 1 : 0);
5889
5874
    if (res)
5895
5880
    join->best_read= 1.0;
5896
5881
  }
5897
5882
  /* Generate an execution plan from the found optimal join order. */
5898
 
  return (join->session->getKilled() || get_best_combination(join));
 
5883
  return (join->session->killed || get_best_combination(join));
5899
5884
}
5900
5885
 
5901
5886
/**
5955
5940
  Return table number if there is only one table in sort order
5956
5941
  and group and order is compatible, else return 0.
5957
5942
*/
5958
 
static Table *get_sort_by_table(Order *a, Order *b,TableList *tables)
 
5943
static Table *get_sort_by_table(order_st *a,order_st *b,TableList *tables)
5959
5944
{
5960
5945
  table_map map= (table_map) 0;
5961
5946
 
6010
5995
  If first parts has different direction, change it to second part
6011
5996
  (group is sorted like order)
6012
5997
*/
6013
 
static bool test_if_subpart(Order *a, Order *b)
 
5998
static bool test_if_subpart(order_st *a,order_st *b)
6014
5999
{
6015
6000
  for (; a && b; a=a->next,b=b->next)
6016
6001
  {