~drizzle-trunk/drizzle/development

« back to all changes in this revision

Viewing changes to drizzled/optimizer/range.cc

  • Committer: Mark Atwood
  • Date: 2011-06-24 02:13:02 UTC
  • mfrom: (2318.6.56 rf)
  • Revision ID: me@mark.atwood.name-20110624021302-y9oiksid220xan9s
mergeĀ lp:~olafvdspek/drizzle/refactor14

Show diffs side-by-side

added added

removed removed

Lines of Context:
696
696
 
697
697
    session->no_errors=1;                               // Don't warn about NULL
698
698
    alloc.init(session->variables.range_alloc_block_size);
699
 
    param.key_parts= (KEY_PART*) alloc.alloc_root( sizeof(KEY_PART) * head->getShare()->key_parts);
 
699
    param.key_parts= (KEY_PART*) alloc.alloc( sizeof(KEY_PART) * head->getShare()->key_parts);
700
700
    if (fill_used_fields_bitmap(&param))
701
701
    {
702
702
      session->no_errors=0;
979
979
  ha_rows roru_total_records;
980
980
  double roru_intersect_part= 1.0;
981
981
 
982
 
  if (! (range_scans= (optimizer::RangeReadPlan**)param->mem_root->alloc_root(sizeof(optimizer::RangeReadPlan*)* n_child_scans)))
983
 
  {
984
 
    return NULL;
985
 
  }
 
982
  range_scans= (optimizer::RangeReadPlan**)param->mem_root->alloc(sizeof(optimizer::RangeReadPlan*)* n_child_scans);
986
983
 
987
984
  /*
988
985
    Collect best 'range' scan for each of disjuncts, and, while doing so,
989
986
    analyze possibility of ROR scans. Also calculate some values needed by
990
987
    other parts of the code.
991
988
  */
992
 
  for (ptree= imerge->trees, cur_child= range_scans;
993
 
       ptree != imerge->trees_next;
994
 
       ptree++, cur_child++)
 
989
  for (ptree= imerge->trees, cur_child= range_scans; ptree != imerge->trees_next; ptree++, cur_child++)
995
990
  {
996
991
    if (!(*cur_child= get_key_scans_params(session, param, *ptree, true, false, read_time)))
997
992
    {
1062
1057
                                    param->session->variables.sortbuff_size);
1063
1058
  if (param->imerge_cost_buff_size < unique_calc_buff_size)
1064
1059
  {
1065
 
    if (!(param->imerge_cost_buff= (uint*)param->mem_root->alloc_root(unique_calc_buff_size)))
1066
 
    {
1067
 
      return NULL;
1068
 
    }
1069
 
 
 
1060
    param->imerge_cost_buff= (uint*)param->mem_root->alloc(unique_calc_buff_size);
1070
1061
    param->imerge_cost_buff_size= unique_calc_buff_size;
1071
1062
  }
1072
1063
 
1094
1085
 
1095
1086
  /* Ok, it is possible to build a ROR-union, try it. */
1096
1087
  bool dummy;
1097
 
  if (! (roru_read_plans=
1098
 
          (optimizer::TableReadPlan **) param->mem_root->alloc_root(sizeof(optimizer::TableReadPlan*) * n_child_scans)))
1099
 
  {
1100
 
    return imerge_trp;
1101
 
  }
 
1088
  roru_read_plans= (optimizer::TableReadPlan **) param->mem_root->alloc(sizeof(optimizer::TableReadPlan*) * n_child_scans);
1102
1089
skip_to_ror_scan:
1103
1090
  roru_index_costs= 0.0;
1104
1091
  roru_total_records= 0;
1209
1196
static
1210
1197
optimizer::RorScanInfo *make_ror_scan(const optimizer::Parameter *param, int idx, optimizer::SEL_ARG *sel_arg)
1211
1198
{
1212
 
  optimizer::RorScanInfo *ror_scan= NULL;
1213
 
 
1214
1199
  uint32_t keynr;
1215
 
 
1216
 
  if (!(ror_scan= (optimizer::RorScanInfo*)param->mem_root->alloc_root(sizeof(optimizer::RorScanInfo))))
1217
 
    return NULL;
 
1200
  optimizer::RorScanInfo* ror_scan= (optimizer::RorScanInfo*)param->mem_root->alloc(sizeof(optimizer::RorScanInfo));
1218
1201
 
1219
1202
  ror_scan->idx= idx;
1220
1203
  ror_scan->keynr= keynr= param->real_keynr[idx];
1711
1694
  if (total_cost > read_time)
1712
1695
    return NULL;
1713
1696
 
1714
 
  optimizer::RorIntersectReadPlan *trp= NULL;
1715
 
  if (! (trp= new (param->mem_root) optimizer::RorIntersectReadPlan))
1716
 
  {
1717
 
    return trp;
1718
 
  }
 
1697
  optimizer::RorIntersectReadPlan* trp= new (param->mem_root) optimizer::RorIntersectReadPlan;
1719
1698
 
1720
1699
  uint32_t best_num= (ror_scan_mark - tree->ror_scans);
1721
 
  if (!(trp->first_scan= (optimizer::RorScanInfo**)param->mem_root->alloc_root(sizeof(optimizer::RorScanInfo*)* best_num)))
1722
 
    return NULL;
 
1700
  trp->first_scan= (optimizer::RorScanInfo**)param->mem_root->alloc(sizeof(optimizer::RorScanInfo*)* best_num);
1723
1701
  memcpy(trp->first_scan, tree->ror_scans, best_num*sizeof(optimizer::RorScanInfo*));
1724
1702
  trp->last_scan=  trp->first_scan + best_num;
1725
1703
  trp->is_covering= true;
1817
1795
  uint32_t cpk_no= 0;
1818
1796
  bool cpk_scan_used= false;
1819
1797
 
1820
 
  if (! (tree->ror_scans= (optimizer::RorScanInfo**)param->mem_root->alloc_root(sizeof(optimizer::RorScanInfo*)* param->keys)))
1821
 
  {
1822
 
    return NULL;
1823
 
  }
1824
 
  cpk_no= ((param->table->cursor->primary_key_is_clustered()) ?
1825
 
           param->table->getShare()->getPrimaryKey() : MAX_KEY);
 
1798
  tree->ror_scans= (optimizer::RorScanInfo**)param->mem_root->alloc(sizeof(optimizer::RorScanInfo*)* param->keys);
 
1799
  cpk_no= ((param->table->cursor->primary_key_is_clustered()) ? param->table->getShare()->getPrimaryKey() : MAX_KEY);
1826
1800
 
1827
1801
  for (idx= 0, cur_ror_scan= tree->ror_scans; idx < param->keys; idx++)
1828
1802
  {
1850
1824
                     (qsort_cmp)cmp_ror_scan_info);
1851
1825
 
1852
1826
  optimizer::RorScanInfo **intersect_scans= NULL; /* ROR scans used in index intersection */
1853
 
  optimizer::RorScanInfo **intersect_scans_end= NULL;
1854
 
  if (! (intersect_scans= (optimizer::RorScanInfo**)param->mem_root->alloc_root(sizeof(optimizer::RorScanInfo*) * tree->n_ror_scans)))
1855
 
    return NULL;
 
1827
  optimizer::RorScanInfo **intersect_scans_end= intersect_scans= 
 
1828
    (optimizer::RorScanInfo**)param->mem_root->alloc(sizeof(optimizer::RorScanInfo*) * tree->n_ror_scans);
1856
1829
  intersect_scans_end= intersect_scans;
1857
1830
 
1858
1831
  /* Create and incrementally update ROR intersection. */
1911
1884
  optimizer::RorIntersectReadPlan *trp= NULL;
1912
1885
  if (min_cost < read_time && (cpk_scan_used || best_num > 1))
1913
1886
  {
1914
 
    if (! (trp= new (param->mem_root) optimizer::RorIntersectReadPlan))
1915
 
      return trp;
1916
 
 
1917
 
    if (! (trp->first_scan=
1918
 
           (optimizer::RorScanInfo**)param->mem_root->alloc_root(sizeof(optimizer::RorScanInfo*)*best_num)))
1919
 
      return NULL;
 
1887
    trp= new (param->mem_root) optimizer::RorIntersectReadPlan;
 
1888
    trp->first_scan= (optimizer::RorScanInfo**)param->mem_root->alloc(sizeof(optimizer::RorScanInfo*)*best_num);
1920
1889
    memcpy(trp->first_scan, intersect_scans, best_num*sizeof(optimizer::RorScanInfo*));
1921
1890
    trp->last_scan=  trp->first_scan + best_num;
1922
1891
    trp->is_covering= intersect_best.is_covering;
2038
2007
 
2039
2008
optimizer::QuickSelectInterface *optimizer::IndexMergeReadPlan::make_quick(optimizer::Parameter *param, bool, memory::Root *)
2040
2009
{
2041
 
  optimizer::QuickIndexMergeSelect *quick_imerge;
2042
 
  optimizer::QuickRangeSelect *quick= NULL;
2043
2010
  /* index_merge always retrieves full rows, ignore retrieve_full_rows */
2044
 
  if (! (quick_imerge= new optimizer::QuickIndexMergeSelect(param->session, param->table)))
2045
 
  {
2046
 
    return NULL;
2047
 
  }
2048
 
 
 
2011
  optimizer::QuickIndexMergeSelect* quick_imerge= new optimizer::QuickIndexMergeSelect(param->session, param->table);
2049
2012
  quick_imerge->records= records;
2050
2013
  quick_imerge->read_time= read_cost;
2051
 
  for (optimizer::RangeReadPlan **range_scan= range_scans; 
2052
 
       range_scan != range_scans_end;
2053
 
       range_scan++)
 
2014
  for (optimizer::RangeReadPlan **range_scan= range_scans; range_scan != range_scans_end; range_scan++)
2054
2015
  {
2055
 
    if (! (quick= (optimizer::QuickRangeSelect*)
2056
 
          ((*range_scan)->make_quick(param, false, &quick_imerge->alloc))) ||
2057
 
        quick_imerge->push_quick_back(quick))
 
2016
    optimizer::QuickRangeSelect* quick= (optimizer::QuickRangeSelect*)((*range_scan)->make_quick(param, false, &quick_imerge->alloc));
 
2017
    if (not quick)
2058
2018
    {
2059
2019
      delete quick;
2060
2020
      delete quick_imerge;
2061
2021
      return NULL;
2062
2022
    }
 
2023
    quick_imerge->push_quick_back(quick);
2063
2024
  }
2064
2025
  return quick_imerge;
2065
2026
}
2086
2047
                                                (*first_scan)->sel_arg,
2087
2048
                                                HA_MRR_USE_DEFAULT_IMPL | HA_MRR_SORTED,
2088
2049
                                                0,
2089
 
                                                alloc)) ||
2090
 
          quick_intersect->push_quick_back(quick))
 
2050
                                                alloc)))
2091
2051
      {
2092
2052
        delete quick_intersect;
2093
2053
        return NULL;
2094
2054
      }
 
2055
      quick_intersect->push_quick_back(quick);
2095
2056
    }
2096
2057
    if (cpk_scan)
2097
2058
    {
2117
2078
 
2118
2079
optimizer::QuickSelectInterface *optimizer::RorUnionReadPlan::make_quick(optimizer::Parameter *param, bool, memory::Root *)
2119
2080
{
2120
 
  optimizer::QuickRorUnionSelect *quick_roru= NULL;
2121
 
  optimizer::TableReadPlan **scan= NULL;
2122
 
  optimizer::QuickSelectInterface *quick= NULL;
2123
2081
  /*
2124
2082
    It is impossible to construct a ROR-union that will not retrieve full
2125
2083
    rows, ignore retrieve_full_rows parameter.
2126
2084
  */
2127
 
  if ((quick_roru= new optimizer::QuickRorUnionSelect(param->session, param->table)))
 
2085
  optimizer::QuickRorUnionSelect* quick_roru= new optimizer::QuickRorUnionSelect(param->session, param->table);
 
2086
  for (optimizer::TableReadPlan** scan= first_ror; scan != last_ror; scan++)
2128
2087
  {
2129
 
    for (scan= first_ror; scan != last_ror; scan++)
2130
 
    {
2131
 
      if (! (quick= (*scan)->make_quick(param, false, &quick_roru->alloc)) ||
2132
 
          quick_roru->push_quick_back(quick))
2133
 
      {
2134
 
        return NULL;
2135
 
      }
2136
 
    }
2137
 
    quick_roru->records= records;
2138
 
    quick_roru->read_time= read_cost;
 
2088
    optimizer::QuickSelectInterface* quick= (*scan)->make_quick(param, false, &quick_roru->alloc);
 
2089
    if (not quick)
 
2090
      return NULL;
 
2091
    quick_roru->push_quick_back(quick);
2139
2092
  }
 
2093
  quick_roru->records= records;
 
2094
  quick_roru->read_time= read_cost;
2140
2095
  return quick_roru;
2141
2096
}
2142
2097
 
2902
2857
        field_length= length;
2903
2858
    }
2904
2859
    length+=offset;
2905
 
    if (!(min_str= (unsigned char*) alloc->alloc_root(length*2)))
2906
 
    {
2907
 
      goto end;
2908
 
    }
2909
 
 
 
2860
    min_str= alloc->alloc(length*2);
2910
2861
    max_str=min_str+length;
2911
2862
    if (maybe_null)
2912
2863
      max_str[0]= min_str[0]=0;
3142
3093
    goto end;
3143
3094
  }
3144
3095
 
3145
 
  str= (unsigned char*) alloc->alloc_root(key_part->store_length+1);
3146
 
  if (!str)
3147
 
    goto end;
 
3096
  str= alloc->alloc(key_part->store_length+1);
3148
3097
  if (maybe_null)
3149
 
    *str= (unsigned char) field->is_real_null();        // Set to 1 if null
 
3098
    *str= field->is_real_null();        // Set to 1 if null
3150
3099
  field->get_key_image(str+maybe_null, key_part->length);
3151
 
  if (! (tree= new (alloc) optimizer::SEL_ARG(field, str, str)))
3152
 
    goto end; // out of memory
 
3100
  tree= new (alloc) optimizer::SEL_ARG(field, str, str);
3153
3101
 
3154
3102
  /*
3155
3103
    Check if we are comparing an UNSIGNED integer with a negative constant.
4013
3961
    {
4014
3962
      quick->mrr_flags= mrr_flags;
4015
3963
      quick->mrr_buf_size= mrr_buf_size;
4016
 
      if (parent_alloc)
4017
 
      {
4018
 
        quick->key_parts= (KEY_PART*)parent_alloc->memdup(param->key[idx], sizeof(KEY_PART)* param->table->key_info[param->real_keynr[idx]].key_parts);
4019
 
      }
4020
 
      else
4021
 
      {
4022
 
        quick->key_parts= (KEY_PART*)quick->alloc.memdup(param->key[idx], sizeof(KEY_PART)* param->table->key_info[param->real_keynr[idx]].key_parts);
4023
 
      }
 
3964
      quick->key_parts= parent_alloc
 
3965
        ? (KEY_PART*)parent_alloc->memdup(param->key[idx], sizeof(KEY_PART)* param->table->key_info[param->real_keynr[idx]].key_parts)
 
3966
        : (KEY_PART*)quick->alloc.memdup(param->key[idx], sizeof(KEY_PART)* param->table->key_info[param->real_keynr[idx]].key_parts);
4024
3967
    }
4025
3968
  }
4026
3969
  return quick;
4276
4219
  range->min_length= range->max_length= ref->key_length;
4277
4220
  range->min_keypart_map= range->max_keypart_map=
4278
4221
    make_prev_keypart_map(ref->key_parts);
4279
 
  range->flag= ((ref->key_length == key_info->key_length &&
4280
 
                 (key_info->flags & HA_END_SPACE_KEY) == 0) ? EQ_RANGE : 0);
4281
 
 
4282
 
 
4283
 
  if (!(quick->key_parts=key_part=(KEY_PART *)
4284
 
        quick->alloc.alloc_root(sizeof(KEY_PART)*ref->key_parts)))
4285
 
    goto err;
 
4222
  range->flag= (ref->key_length == key_info->key_length && (key_info->flags & HA_END_SPACE_KEY) == 0) ? EQ_RANGE : 0;
 
4223
 
 
4224
  quick->key_parts=key_part=(KEY_PART *)quick->alloc.alloc(sizeof(KEY_PART)*ref->key_parts);
4286
4225
 
4287
4226
  for (part=0 ; part < ref->key_parts ;part++,key_part++)
4288
4227
  {
5468
5407
optimizer::QuickSelectInterface *
5469
5408
optimizer::GroupMinMaxReadPlan::make_quick(optimizer::Parameter *param, bool, memory::Root *parent_alloc)
5470
5409
{
5471
 
  optimizer::QuickGroupMinMaxSelect *quick= NULL;
5472
 
 
5473
 
  quick= new optimizer::QuickGroupMinMaxSelect(param->table,
 
5410
  optimizer::QuickGroupMinMaxSelect *quick= new optimizer::QuickGroupMinMaxSelect(param->table,
5474
5411
                                               param->session->lex().current_select->join,
5475
5412
                                               have_min,
5476
5413
                                               have_max,
5485
5422
                                               key_infix_len,
5486
5423
                                               key_infix,
5487
5424
                                               parent_alloc);
5488
 
  if (! quick)
5489
 
  {
5490
 
    return NULL;
5491
 
  }
5492
 
 
5493
5425
  if (quick->init())
5494
5426
  {
5495
5427
    delete quick;