~drizzle-trunk/drizzle/development

« back to all changes in this revision

Viewing changes to drizzled/item/sum.cc

  • Committer: Brian Aker
  • Date: 2009-05-11 17:50:22 UTC
  • Revision ID: brian@gaz-20090511175022-y35q9ky6uh9ldcjt
Replacing Sun employee copyright headers (aka... anything done by a Sun
employee is copyright by Sun).

Show diffs side-by-side

added added

removed removed

Lines of Context:
11
11
 
12
12
   You should have received a copy of the GNU General Public License
13
13
   along with this program; if not, write to the Free Software
14
 
   Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA */
 
14
   Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA */
15
15
 
16
16
 
17
17
/**
20
20
  @brief
21
21
  Sum functions (COUNT, MIN...)
22
22
*/
23
 
#include "config.h"
24
 
#include <cstdio>
25
 
#include <math.h>
 
23
#include <drizzled/server_includes.h>
26
24
#include <drizzled/sql_select.h>
27
25
#include <drizzled/error.h>
28
26
#include <drizzled/hybrid_type_traits.h>
33
31
#include <drizzled/item/sum.h>
34
32
#include <drizzled/field/decimal.h>
35
33
#include <drizzled/field/double.h>
36
 
#include <drizzled/field/int64.h>
 
34
#include <drizzled/field/int64_t.h>
37
35
#include <drizzled/field/date.h>
38
36
#include <drizzled/field/datetime.h>
39
37
 
40
 
#include "drizzled/internal/m_string.h"
41
 
 
42
 
#include <algorithm>
43
 
 
44
 
using namespace std;
45
 
 
46
 
namespace drizzled
47
 
{
48
 
 
49
38
extern my_decimal decimal_zero;
50
 
extern plugin::StorageEngine *heap_engine;
51
39
 
52
40
/**
53
41
  Prepare an aggregate function item for checking context conditions.
268
256
          in_sum_func->outer_fields.push_back(field);
269
257
        }
270
258
        else
271
 
        {
272
 
          sel->full_group_by_flag.set(NON_AGG_FIELD_USED);
273
 
        }
 
259
          sel->full_group_by_flag|= NON_AGG_FIELD_USED;
274
260
      }
275
261
      if (sel->nest_level > aggr_level &&
276
 
          (sel->full_group_by_flag.test(SUM_FUNC_USED)) &&
277
 
          ! sel->group_list.elements)
 
262
          (sel->full_group_by_flag & SUM_FUNC_USED) &&
 
263
          !sel->group_list.elements)
278
264
      {
279
265
        my_message(ER_MIX_OF_GROUP_FUNC_AND_FIELDS,
280
266
                   ER(ER_MIX_OF_GROUP_FUNC_AND_FIELDS), MYF(0));
282
268
      }
283
269
    }
284
270
  }
285
 
  aggr_sel->full_group_by_flag.set(SUM_FUNC_USED);
 
271
  aggr_sel->full_group_by_flag|= SUM_FUNC_USED;
286
272
  update_used_tables();
287
273
  session->lex->in_sum_func= in_sum_func;
288
274
  return false;
381
367
Item_sum::Item_sum(List<Item> &list) :arg_count(list.elements),
382
368
  forced_const(false)
383
369
{
384
 
  if ((args=(Item**) memory::sql_alloc(sizeof(Item*)*arg_count)))
 
370
  if ((args=(Item**) sql_alloc(sizeof(Item*)*arg_count)))
385
371
  {
386
372
    uint32_t i=0;
387
373
    List_iterator_fast<Item> li(list);
426
412
}
427
413
 
428
414
 
429
 
void Item_sum::make_field(SendField *tmp_field)
 
415
void Item_sum::make_field(Send_field *tmp_field)
430
416
{
431
417
  if (args[0]->type() == Item::FIELD_ITEM && keep_field_type())
432
418
  {
508
494
                                  Table *table,
509
495
                                  uint32_t convert_blob_length)
510
496
{
511
 
  Field *field= NULL;
512
 
 
 
497
  Field *field;
513
498
  switch (result_type()) {
514
499
  case REAL_RESULT:
515
500
    field= new Field_double(max_length, maybe_null, name, decimals, true);
516
501
    break;
517
 
 
518
502
  case INT_RESULT:
519
 
    field= new field::Int64(max_length, maybe_null, name, unsigned_flag);
 
503
    field= new Field_int64_t(max_length, maybe_null, name, unsigned_flag);
520
504
    break;
521
 
 
522
505
  case STRING_RESULT:
523
506
    if (max_length/collation.collation->mbmaxlen <= 255 ||
524
507
        convert_blob_length > Field_varstring::MAX_SIZE ||
525
508
        !convert_blob_length)
526
 
    {
527
509
      return make_string_field(table);
528
 
    }
529
 
 
530
 
    table->setVariableWidth();
531
510
    field= new Field_varstring(convert_blob_length, maybe_null,
532
 
                               name, collation.collation);
 
511
                               name, table->s, collation.collation);
533
512
    break;
534
 
 
535
513
  case DECIMAL_RESULT:
536
 
    field= new Field_decimal(max_length, maybe_null, name,
537
 
                             decimals, unsigned_flag);
 
514
    field= new Field_new_decimal(max_length, maybe_null, name,
 
515
                                 decimals, unsigned_flag);
538
516
    break;
539
 
 
540
517
  case ROW_RESULT:
 
518
  default:
541
519
    // This case should never be choosen
542
520
    assert(0);
543
521
    return 0;
544
522
  }
545
 
 
546
523
  if (field)
547
524
    field->init(table);
548
 
 
549
525
  return field;
550
526
}
551
527
 
655
631
    */
656
632
    break;
657
633
  case ROW_RESULT:
 
634
  default:
658
635
    assert(0);
659
636
  }
660
637
  collation.set(item->collation);
693
670
    max_length= item->max_length;
694
671
    break;
695
672
  case ROW_RESULT:
 
673
  default:
696
674
    assert(0);
697
675
  };
698
676
  /* MIN/MAX can return NULL for empty set indepedent of the used column */
804
782
    break;
805
783
  case INT_RESULT:
806
784
  case DECIMAL_RESULT:
807
 
    {
808
 
      /* SUM result can't be longer than length(arg) + length(MAX_ROWS) */
809
 
      int precision= args[0]->decimal_precision() + DECIMAL_LONGLONG_DIGITS;
810
 
      max_length= my_decimal_precision_to_length(precision, decimals,
811
 
                                                 unsigned_flag);
812
 
      curr_dec_buff= 0;
813
 
      hybrid_type= DECIMAL_RESULT;
814
 
      my_decimal_set_zero(dec_buffs);
815
 
      break;
816
 
    }
 
785
  {
 
786
    /* SUM result can't be longer than length(arg) + length(MAX_ROWS) */
 
787
    int precision= args[0]->decimal_precision() + DECIMAL_LONGLONG_DIGITS;
 
788
    max_length= my_decimal_precision_to_length(precision, decimals,
 
789
                                               unsigned_flag);
 
790
    curr_dec_buff= 0;
 
791
    hybrid_type= DECIMAL_RESULT;
 
792
    my_decimal_set_zero(dec_buffs);
 
793
    break;
 
794
  }
817
795
  case ROW_RESULT:
 
796
  default:
818
797
    assert(0);
819
798
  }
 
799
  return;
820
800
}
821
801
 
822
802
 
883
863
 
884
864
/***************************************************************************/
885
865
 
 
866
#ifdef __cplusplus
 
867
extern "C" {
 
868
#endif
 
869
 
886
870
/* Declarations for auxilary C-callbacks */
887
871
 
888
872
static int simple_raw_key_cmp(void* arg, const void* key1, const void* key2)
892
876
 
893
877
 
894
878
static int item_sum_distinct_walk(void *element,
895
 
                                  uint32_t ,
 
879
                                  element_count ,
896
880
                                  void *item)
897
881
{
898
882
  return ((Item_sum_distinct*) (item))->unique_walk_function(element);
899
883
}
900
884
 
 
885
#ifdef __cplusplus
 
886
}
 
887
#endif
 
888
 
901
889
/* Item_sum_distinct */
902
890
 
903
891
Item_sum_distinct::Item_sum_distinct(Item *item_arg)
959
947
{
960
948
  assert(args[0]->fixed);
961
949
 
962
 
  null_value= maybe_null= true;
963
950
  table_field_type= args[0]->field_type();
964
951
 
965
952
  /* Adjust tmp table type according to the chosen aggregation type */
970
957
    table_field_type= DRIZZLE_TYPE_DOUBLE;
971
958
    break;
972
959
  case INT_RESULT:
973
 
    /*
974
 
      Preserving int8, int16, int32 field types gives ~10% performance boost
975
 
      as the size of result tree becomes significantly smaller.
976
 
      Another speed up we gain by using int64_t for intermediate
977
 
      calculations. The range of int64 is enough to hold sum 2^32 distinct
978
 
      integers each <= 2^32.
979
 
    */
980
 
    if (table_field_type == DRIZZLE_TYPE_LONG)
981
 
    {
982
 
      val.traits= Hybrid_type_traits_fast_decimal::instance();
983
 
      break;
984
 
    }
985
 
    table_field_type= DRIZZLE_TYPE_LONGLONG;
986
 
    /* fallthrough */
 
960
  /*
 
961
    Preserving int8, int16, int32 field types gives ~10% performance boost
 
962
    as the size of result tree becomes significantly smaller.
 
963
    Another speed up we gain by using int64_t for intermediate
 
964
    calculations. The range of int64 is enough to hold sum 2^32 distinct
 
965
    integers each <= 2^32.
 
966
  */
 
967
  if (table_field_type == DRIZZLE_TYPE_LONG)
 
968
  {
 
969
    val.traits= Hybrid_type_traits_fast_decimal::instance();
 
970
    break;
 
971
  }
 
972
  table_field_type= DRIZZLE_TYPE_LONGLONG;
 
973
  /* fallthrough */
987
974
  case DECIMAL_RESULT:
988
975
    val.traits= Hybrid_type_traits_decimal::instance();
989
976
    if (table_field_type != DRIZZLE_TYPE_LONGLONG)
990
 
      table_field_type= DRIZZLE_TYPE_DECIMAL;
 
977
      table_field_type= DRIZZLE_TYPE_NEWDECIMAL;
991
978
    break;
992
979
  case ROW_RESULT:
 
980
  default:
993
981
    assert(0);
994
982
  }
995
 
 
996
983
  val.traits->fix_length_and_dec(this, args[0]);
997
984
}
998
985
 
1009
996
*/
1010
997
bool Item_sum_distinct::setup(Session *session)
1011
998
{
1012
 
  List<CreateField> field_list;
1013
 
  CreateField field_def;                              /* field definition */
 
999
  List<Create_field> field_list;
 
1000
  Create_field field_def;                              /* field definition */
1014
1001
  /* It's legal to call setup() more than once when in a subquery */
1015
1002
  if (tree)
1016
1003
    return(false);
1029
1016
  assert(args[0]->fixed);
1030
1017
 
1031
1018
  field_def.init_for_tmp_table(table_field_type, args[0]->max_length,
1032
 
                               args[0]->decimals, args[0]->maybe_null);
 
1019
                               args[0]->decimals, args[0]->maybe_null,
 
1020
                               args[0]->unsigned_flag);
1033
1021
 
1034
 
  if (! (table= session->getInstanceTable(field_list)))
 
1022
  if (! (table= create_virtual_tmp_table(session, field_list)))
1035
1023
    return(true);
1036
1024
 
1037
1025
  /* XXX: check that the case of CHAR(0) works OK */
1038
 
  tree_key_length= table->getShare()->getRecordLength() - table->getShare()->null_bytes;
 
1026
  tree_key_length= table->s->reclength - table->s->null_bytes;
1039
1027
 
1040
1028
  /*
1041
1029
    Unique handles all unique elements in a tree until they can't fit
1054
1042
 
1055
1043
bool Item_sum_distinct::add()
1056
1044
{
1057
 
  args[0]->save_in_field(table->getField(0), false);
 
1045
  args[0]->save_in_field(table->field[0], false);
1058
1046
  is_evaluated= false;
1059
 
  if (!table->getField(0)->is_null())
 
1047
  if (!table->field[0]->is_null())
1060
1048
  {
1061
1049
    assert(tree);
1062
1050
    null_value= 0;
1064
1052
      '0' values are also stored in the tree. This doesn't matter
1065
1053
      for SUM(DISTINCT), but is important for AVG(DISTINCT)
1066
1054
    */
1067
 
    return tree->unique_add(table->getField(0)->ptr);
 
1055
    return tree->unique_add(table->field[0]->ptr);
1068
1056
  }
1069
1057
  return 0;
1070
1058
}
1072
1060
 
1073
1061
bool Item_sum_distinct::unique_walk_function(void *element)
1074
1062
{
1075
 
  memcpy(table->getField(0)->ptr, element, tree_key_length);
 
1063
  memcpy(table->field[0]->ptr, element, tree_key_length);
1076
1064
  ++count;
1077
 
  val.traits->add(&val, table->getField(0));
 
1065
  val.traits->add(&val, table->field[0]);
1078
1066
  return 0;
1079
1067
}
1080
1068
 
1116
1104
     */
1117
1105
    if (tree)
1118
1106
    {
1119
 
      table->getField(0)->set_notnull();
 
1107
      table->field[0]->set_notnull();
1120
1108
      tree->walk(item_sum_distinct_walk, (void*) this);
1121
1109
    }
1122
1110
    is_evaluated= true;
1168
1156
    AVG() will divide val by count. We need to reserve digits
1169
1157
    after decimal point as the result can be fractional.
1170
1158
  */
1171
 
  decimals= min(decimals + prec_increment, (unsigned int)NOT_FIXED_DEC);
 
1159
  decimals= cmin(decimals + prec_increment, (unsigned int)NOT_FIXED_DEC);
1172
1160
}
1173
1161
 
1174
1162
 
1230
1218
  if (hybrid_type == DECIMAL_RESULT)
1231
1219
  {
1232
1220
    int precision= args[0]->decimal_precision() + prec_increment;
1233
 
    decimals= min(args[0]->decimals + prec_increment, (unsigned int) DECIMAL_MAX_SCALE);
 
1221
    decimals= cmin(args[0]->decimals + prec_increment, (unsigned int) DECIMAL_MAX_SCALE);
1234
1222
    max_length= my_decimal_precision_to_length(precision, decimals,
1235
1223
                                               unsigned_flag);
1236
 
    f_precision= min(precision+DECIMAL_LONGLONG_DIGITS, DECIMAL_MAX_PRECISION);
 
1224
    f_precision= cmin(precision+DECIMAL_LONGLONG_DIGITS, DECIMAL_MAX_PRECISION);
1237
1225
    f_scale=  args[0]->decimals;
1238
1226
    dec_bin_size= my_decimal_get_binary_size(f_precision, f_scale);
1239
1227
  }
1240
1228
  else {
1241
 
    decimals= min(args[0]->decimals + prec_increment, (unsigned int) NOT_FIXED_DEC);
 
1229
    decimals= cmin(args[0]->decimals + prec_increment, (unsigned int) NOT_FIXED_DEC);
1242
1230
    max_length= args[0]->max_length + prec_increment;
1243
1231
  }
1244
1232
}
1261
1249
      The easiest way is to do this is to store both value in a string
1262
1250
      and unpack on access.
1263
1251
    */
1264
 
    table->setVariableWidth();
1265
1252
    field= new Field_varstring(((hybrid_type == DECIMAL_RESULT) ?
1266
1253
                                dec_bin_size : sizeof(double)) + sizeof(int64_t),
1267
 
                               0, name, &my_charset_bin);
 
1254
                               0, name, table->s, &my_charset_bin);
1268
1255
  }
1269
1256
  else if (hybrid_type == DECIMAL_RESULT)
1270
 
    field= new Field_decimal(max_length, maybe_null, name,
1271
 
                             decimals, unsigned_flag);
 
1257
    field= new Field_new_decimal(max_length, maybe_null, name,
 
1258
                                 decimals, unsigned_flag);
1272
1259
  else
1273
1260
    field= new Field_double(max_length, maybe_null, name, decimals, true);
1274
1261
  if (field)
1436
1423
  switch (args[0]->result_type()) {
1437
1424
  case REAL_RESULT:
1438
1425
  case STRING_RESULT:
1439
 
    decimals= min(args[0]->decimals + 4, (int)NOT_FIXED_DEC);
 
1426
    decimals= cmin(args[0]->decimals + 4, NOT_FIXED_DEC);
1440
1427
    break;
1441
1428
  case INT_RESULT:
1442
1429
  case DECIMAL_RESULT:
1443
 
    {
1444
 
      int precision= args[0]->decimal_precision()*2 + prec_increment;
1445
 
      decimals= min(args[0]->decimals + prec_increment, (unsigned int) DECIMAL_MAX_SCALE);
1446
 
      max_length= my_decimal_precision_to_length(precision, decimals,
1447
 
                                                 unsigned_flag);
 
1430
  {
 
1431
    int precision= args[0]->decimal_precision()*2 + prec_increment;
 
1432
    decimals= cmin(args[0]->decimals + prec_increment, (unsigned int) DECIMAL_MAX_SCALE);
 
1433
    max_length= my_decimal_precision_to_length(precision, decimals,
 
1434
                                               unsigned_flag);
1448
1435
 
1449
 
      break;
1450
 
    }
 
1436
    break;
 
1437
  }
1451
1438
  case ROW_RESULT:
 
1439
  default:
1452
1440
    assert(0);
1453
1441
  }
 
1442
  return;
1454
1443
}
1455
1444
 
1456
1445
 
1476
1465
      The easiest way is to do this is to store both value in a string
1477
1466
      and unpack on access.
1478
1467
    */
1479
 
    table->setVariableWidth();
1480
 
    field= new Field_varstring(sizeof(double)*2 + sizeof(int64_t), 0, name, &my_charset_bin);
 
1468
    field= new Field_varstring(sizeof(double)*2 + sizeof(int64_t), 0, name, table->s, &my_charset_bin);
1481
1469
  }
1482
1470
  else
1483
1471
    field= new Field_double(max_length, maybe_null, name, decimals, true);
1619
1607
  assert(fixed == 1);
1620
1608
  if (null_value)
1621
1609
    return 0.0;
1622
 
 
1623
1610
  switch (hybrid_type) {
1624
1611
  case STRING_RESULT:
1625
 
    {
1626
 
      char *end_not_used;
1627
 
      int err_not_used;
1628
 
      String *res;  res=val_str(&str_value);
1629
 
      return (res ? my_strntod(res->charset(), (char*) res->ptr(), res->length(),
1630
 
                               &end_not_used, &err_not_used) : 0.0);
1631
 
    }
 
1612
  {
 
1613
    char *end_not_used;
 
1614
    int err_not_used;
 
1615
    String *res;  res=val_str(&str_value);
 
1616
    return (res ? my_strntod(res->charset(), (char*) res->ptr(), res->length(),
 
1617
                             &end_not_used, &err_not_used) : 0.0);
 
1618
  }
1632
1619
  case INT_RESULT:
1633
1620
    return (double) sum_int;
1634
1621
  case DECIMAL_RESULT:
1637
1624
  case REAL_RESULT:
1638
1625
    return sum;
1639
1626
  case ROW_RESULT:
 
1627
  default:
1640
1628
    // This case should never be choosen
1641
 
    break;
 
1629
    assert(0);
 
1630
    return 0;
1642
1631
  }
1643
 
 
1644
 
  assert(0);
1645
 
  return 0;
1646
1632
}
1647
1633
 
1648
1634
int64_t Item_sum_hybrid::val_int()
1670
1656
  assert(fixed == 1);
1671
1657
  if (null_value)
1672
1658
    return 0;
1673
 
 
1674
1659
  switch (hybrid_type) {
1675
1660
  case STRING_RESULT:
1676
1661
    string2my_decimal(E_DEC_FATAL_ERROR, &value, val);
1685
1670
    int2my_decimal(E_DEC_FATAL_ERROR, sum_int, unsigned_flag, val);
1686
1671
    break;
1687
1672
  case ROW_RESULT:
 
1673
  default:
1688
1674
    // This case should never be choosen
1689
1675
    assert(0);
1690
1676
    break;
1691
1677
  }
1692
 
 
1693
1678
  return val;                                   // Keep compiler happy
1694
1679
}
1695
1680
 
1700
1685
  assert(fixed == 1);
1701
1686
  if (null_value)
1702
1687
    return 0;
1703
 
 
1704
1688
  switch (hybrid_type) {
1705
1689
  case STRING_RESULT:
1706
1690
    return &value;
1716
1700
  case ROW_RESULT:
1717
1701
  default:
1718
1702
    // This case should never be choosen
 
1703
    assert(0);
1719
1704
    break;
1720
1705
  }
1721
 
 
1722
1706
  return str;                                   // Keep compiler happy
1723
1707
}
1724
1708
 
1756
1740
{
1757
1741
  switch (hybrid_type) {
1758
1742
  case STRING_RESULT:
 
1743
  {
 
1744
    String *result=args[0]->val_str(&tmp_value);
 
1745
    if (!args[0]->null_value &&
 
1746
        (null_value || sortcmp(&value,result,collation.collation) > 0))
1759
1747
    {
1760
 
      String *result=args[0]->val_str(&tmp_value);
1761
 
      if (!args[0]->null_value &&
1762
 
          (null_value || sortcmp(&value,result,collation.collation) > 0))
1763
 
      {
1764
 
        value.copy(*result);
1765
 
        null_value=0;
1766
 
      }
 
1748
      value.copy(*result);
 
1749
      null_value=0;
1767
1750
    }
1768
 
    break;
 
1751
  }
 
1752
  break;
1769
1753
  case INT_RESULT:
 
1754
  {
 
1755
    int64_t nr=args[0]->val_int();
 
1756
    if (!args[0]->null_value && (null_value ||
 
1757
                                 (unsigned_flag &&
 
1758
                                  (uint64_t) nr < (uint64_t) sum_int) ||
 
1759
                                 (!unsigned_flag && nr < sum_int)))
1770
1760
    {
1771
 
      int64_t nr=args[0]->val_int();
1772
 
      if (!args[0]->null_value && (null_value ||
1773
 
                                   (unsigned_flag &&
1774
 
                                    (uint64_t) nr < (uint64_t) sum_int) ||
1775
 
                                   (!unsigned_flag && nr < sum_int)))
1776
 
      {
1777
 
        sum_int=nr;
1778
 
        null_value=0;
1779
 
      }
 
1761
      sum_int=nr;
 
1762
      null_value=0;
1780
1763
    }
1781
 
    break;
 
1764
  }
 
1765
  break;
1782
1766
  case DECIMAL_RESULT:
 
1767
  {
 
1768
    my_decimal value_buff, *val= args[0]->val_decimal(&value_buff);
 
1769
    if (!args[0]->null_value &&
 
1770
        (null_value || (my_decimal_cmp(&sum_dec, val) > 0)))
1783
1771
    {
1784
 
      my_decimal value_buff, *val= args[0]->val_decimal(&value_buff);
1785
 
      if (!args[0]->null_value &&
1786
 
          (null_value || (my_decimal_cmp(&sum_dec, val) > 0)))
1787
 
      {
1788
 
        my_decimal2decimal(val, &sum_dec);
1789
 
        null_value= 0;
1790
 
      }
 
1772
      my_decimal2decimal(val, &sum_dec);
 
1773
      null_value= 0;
1791
1774
    }
1792
 
    break;
 
1775
  }
 
1776
  break;
1793
1777
  case REAL_RESULT:
 
1778
  {
 
1779
    double nr= args[0]->val_real();
 
1780
    if (!args[0]->null_value && (null_value || nr < sum))
1794
1781
    {
1795
 
      double nr= args[0]->val_real();
1796
 
      if (!args[0]->null_value && (null_value || nr < sum))
1797
 
      {
1798
 
        sum=nr;
1799
 
        null_value=0;
1800
 
      }
 
1782
      sum=nr;
 
1783
      null_value=0;
1801
1784
    }
1802
 
    break;
 
1785
  }
 
1786
  break;
1803
1787
  case ROW_RESULT:
 
1788
  default:
1804
1789
    // This case should never be choosen
1805
1790
    assert(0);
1806
1791
    break;
1819
1804
{
1820
1805
  switch (hybrid_type) {
1821
1806
  case STRING_RESULT:
 
1807
  {
 
1808
    String *result=args[0]->val_str(&tmp_value);
 
1809
    if (!args[0]->null_value &&
 
1810
        (null_value || sortcmp(&value,result,collation.collation) < 0))
1822
1811
    {
1823
 
      String *result=args[0]->val_str(&tmp_value);
1824
 
      if (!args[0]->null_value &&
1825
 
          (null_value || sortcmp(&value,result,collation.collation) < 0))
1826
 
      {
1827
 
        value.copy(*result);
1828
 
        null_value=0;
1829
 
      }
 
1812
      value.copy(*result);
 
1813
      null_value=0;
1830
1814
    }
1831
 
    break;
 
1815
  }
 
1816
  break;
1832
1817
  case INT_RESULT:
 
1818
  {
 
1819
    int64_t nr=args[0]->val_int();
 
1820
    if (!args[0]->null_value && (null_value ||
 
1821
                                 (unsigned_flag &&
 
1822
                                  (uint64_t) nr > (uint64_t) sum_int) ||
 
1823
                                 (!unsigned_flag && nr > sum_int)))
1833
1824
    {
1834
 
      int64_t nr=args[0]->val_int();
1835
 
      if (!args[0]->null_value && (null_value ||
1836
 
                                   (unsigned_flag &&
1837
 
                                    (uint64_t) nr > (uint64_t) sum_int) ||
1838
 
                                   (!unsigned_flag && nr > sum_int)))
1839
 
      {
1840
 
        sum_int=nr;
1841
 
        null_value=0;
1842
 
      }
 
1825
      sum_int=nr;
 
1826
      null_value=0;
1843
1827
    }
1844
 
    break;
 
1828
  }
 
1829
  break;
1845
1830
  case DECIMAL_RESULT:
 
1831
  {
 
1832
    my_decimal value_buff, *val= args[0]->val_decimal(&value_buff);
 
1833
    if (!args[0]->null_value &&
 
1834
        (null_value || (my_decimal_cmp(val, &sum_dec) > 0)))
1846
1835
    {
1847
 
      my_decimal value_buff, *val= args[0]->val_decimal(&value_buff);
1848
 
      if (!args[0]->null_value &&
1849
 
          (null_value || (my_decimal_cmp(val, &sum_dec) > 0)))
1850
 
      {
1851
 
        my_decimal2decimal(val, &sum_dec);
1852
 
        null_value= 0;
1853
 
      }
 
1836
      my_decimal2decimal(val, &sum_dec);
 
1837
      null_value= 0;
1854
1838
    }
1855
 
    break;
 
1839
  }
 
1840
  break;
1856
1841
  case REAL_RESULT:
 
1842
  {
 
1843
    double nr= args[0]->val_real();
 
1844
    if (!args[0]->null_value && (null_value || nr > sum))
1857
1845
    {
1858
 
      double nr= args[0]->val_real();
1859
 
      if (!args[0]->null_value && (null_value || nr > sum))
1860
 
      {
1861
 
        sum=nr;
1862
 
        null_value=0;
1863
 
      }
 
1846
      sum=nr;
 
1847
      null_value=0;
1864
1848
    }
1865
 
    break;
 
1849
  }
 
1850
  break;
1866
1851
  case ROW_RESULT:
 
1852
  default:
1867
1853
    // This case should never be choosen
1868
1854
    assert(0);
1869
1855
    break;
1870
1856
  }
1871
 
 
1872
1857
  return 0;
1873
1858
}
1874
1859
 
1956
1941
{
1957
1942
  switch(hybrid_type) {
1958
1943
  case STRING_RESULT:
1959
 
    {
1960
 
      char buff[MAX_FIELD_WIDTH];
1961
 
      String tmp(buff,sizeof(buff),result_field->charset()),*res;
1962
 
 
1963
 
      res=args[0]->val_str(&tmp);
1964
 
      if (args[0]->null_value)
1965
 
      {
 
1944
  {
 
1945
    char buff[MAX_FIELD_WIDTH];
 
1946
    String tmp(buff,sizeof(buff),result_field->charset()),*res;
 
1947
 
 
1948
    res=args[0]->val_str(&tmp);
 
1949
    if (args[0]->null_value)
 
1950
    {
 
1951
      result_field->set_null();
 
1952
      result_field->reset();
 
1953
    }
 
1954
    else
 
1955
    {
 
1956
      result_field->set_notnull();
 
1957
      result_field->store(res->ptr(),res->length(),tmp.charset());
 
1958
    }
 
1959
    break;
 
1960
  }
 
1961
  case INT_RESULT:
 
1962
  {
 
1963
    int64_t nr=args[0]->val_int();
 
1964
 
 
1965
    if (maybe_null)
 
1966
    {
 
1967
      if (args[0]->null_value)
 
1968
      {
 
1969
        nr=0;
 
1970
        result_field->set_null();
 
1971
      }
 
1972
      else
 
1973
        result_field->set_notnull();
 
1974
    }
 
1975
    result_field->store(nr, unsigned_flag);
 
1976
    break;
 
1977
  }
 
1978
  case REAL_RESULT:
 
1979
  {
 
1980
    double nr= args[0]->val_real();
 
1981
 
 
1982
    if (maybe_null)
 
1983
    {
 
1984
      if (args[0]->null_value)
 
1985
      {
 
1986
        nr=0.0;
 
1987
        result_field->set_null();
 
1988
      }
 
1989
      else
 
1990
        result_field->set_notnull();
 
1991
    }
 
1992
    result_field->store(nr);
 
1993
    break;
 
1994
  }
 
1995
  case DECIMAL_RESULT:
 
1996
  {
 
1997
    my_decimal value_buff, *arg_dec= args[0]->val_decimal(&value_buff);
 
1998
 
 
1999
    if (maybe_null)
 
2000
    {
 
2001
      if (args[0]->null_value)
1966
2002
        result_field->set_null();
1967
 
        result_field->reset();
1968
 
      }
1969
2003
      else
1970
 
      {
1971
2004
        result_field->set_notnull();
1972
 
        result_field->store(res->ptr(),res->length(),tmp.charset());
1973
 
      }
1974
 
      break;
1975
 
    }
1976
 
  case INT_RESULT:
1977
 
    {
1978
 
      int64_t nr=args[0]->val_int();
1979
 
 
1980
 
      if (maybe_null)
1981
 
      {
1982
 
        if (args[0]->null_value)
1983
 
        {
1984
 
          nr=0;
1985
 
          result_field->set_null();
1986
 
        }
1987
 
        else
1988
 
          result_field->set_notnull();
1989
 
      }
1990
 
      result_field->store(nr, unsigned_flag);
1991
 
      break;
1992
 
    }
1993
 
  case REAL_RESULT:
1994
 
    {
1995
 
      double nr= args[0]->val_real();
1996
 
 
1997
 
      if (maybe_null)
1998
 
      {
1999
 
        if (args[0]->null_value)
2000
 
        {
2001
 
          nr=0.0;
2002
 
          result_field->set_null();
2003
 
        }
2004
 
        else
2005
 
          result_field->set_notnull();
2006
 
      }
2007
 
      result_field->store(nr);
2008
 
      break;
2009
 
    }
2010
 
  case DECIMAL_RESULT:
2011
 
    {
2012
 
      my_decimal value_buff, *arg_dec= args[0]->val_decimal(&value_buff);
2013
 
 
2014
 
      if (maybe_null)
2015
 
      {
2016
 
        if (args[0]->null_value)
2017
 
          result_field->set_null();
2018
 
        else
2019
 
          result_field->set_notnull();
2020
 
      }
2021
 
      /*
2022
 
        We must store zero in the field as we will use the field value in
2023
 
        add()
2024
 
      */
2025
 
      if (!arg_dec)                               // Null
2026
 
        arg_dec= &decimal_zero;
2027
 
      result_field->store_decimal(arg_dec);
2028
 
      break;
2029
 
    }
 
2005
    }
 
2006
    /*
 
2007
      We must store zero in the field as we will use the field value in
 
2008
      add()
 
2009
    */
 
2010
    if (!arg_dec)                               // Null
 
2011
      arg_dec= &decimal_zero;
 
2012
    result_field->store_decimal(arg_dec);
 
2013
    break;
 
2014
  }
2030
2015
  case ROW_RESULT:
 
2016
  default:
2031
2017
    assert(0);
2032
2018
  }
2033
2019
}
2222
2208
  case DECIMAL_RESULT:
2223
2209
    min_max_update_decimal_field();
2224
2210
    break;
2225
 
  case REAL_RESULT:
2226
 
  case ROW_RESULT:
 
2211
  default:
2227
2212
    min_max_update_real_field();
2228
2213
  }
2229
2214
}
2236
2221
 
2237
2222
  if (!args[0]->null_value)
2238
2223
  {
2239
 
    result_field->val_str_internal(&tmp_value);
 
2224
    result_field->val_str(&tmp_value);
2240
2225
 
2241
2226
    if (result_field->is_null() ||
2242
2227
        (cmp_sign * sortcmp(res_str,&tmp_value,collation.collation)) < 0)
2503
2488
int composite_key_cmp(void* arg, unsigned char* key1, unsigned char* key2)
2504
2489
{
2505
2490
  Item_sum_count_distinct* item = (Item_sum_count_distinct*)arg;
2506
 
  Field **field    = item->table->getFields();
2507
 
  Field **field_end= field + item->table->getShare()->sizeFields();
 
2491
  Field **field    = item->table->field;
 
2492
  Field **field_end= field + item->table->s->fields;
2508
2493
  uint32_t *lengths=item->field_lengths;
2509
2494
  for (; field < field_end; ++field)
2510
2495
  {
2519
2504
  return 0;
2520
2505
}
2521
2506
 
 
2507
#ifdef __cplusplus
 
2508
extern "C" {
 
2509
#endif
 
2510
 
2522
2511
static int count_distinct_walk(void *,
2523
 
                               uint32_t ,
 
2512
                               element_count ,
2524
2513
                               void *arg)
2525
2514
{
2526
2515
  (*((uint64_t*)arg))++;
2527
2516
  return 0;
2528
2517
}
2529
2518
 
 
2519
#ifdef __cplusplus
 
2520
}
 
2521
#endif
 
2522
 
 
2523
 
 
2524
 
2530
2525
void Item_sum_count_distinct::cleanup()
2531
2526
{
2532
2527
  Item_sum_int::cleanup();
2544
2539
    is_evaluated= false;
2545
2540
    if (table)
2546
2541
    {
 
2542
      table->free_tmp_table(table->in_use);
2547
2543
      table= 0;
2548
2544
    }
2549
2545
    delete tmp_table_param;
2608
2604
  tmp_table_param->force_copy_fields= force_copy_fields;
2609
2605
  assert(table == 0);
2610
2606
 
2611
 
  if (!(table= create_tmp_table(session, tmp_table_param, list, (Order*) 0, 1,
 
2607
  if (!(table= create_tmp_table(session, tmp_table_param, list, (order_st*) 0, 1,
2612
2608
                                0,
2613
2609
                                (select_lex->options | session->options),
2614
2610
                                HA_POS_ERROR, (char*)"")))
2615
 
  {
2616
2611
    return true;
2617
 
  }
2618
 
  table->cursor->extra(HA_EXTRA_NO_ROWS);               // Don't update rows
 
2612
  table->file->extra(HA_EXTRA_NO_ROWS);         // Don't update rows
2619
2613
  table->no_rows=1;
2620
2614
 
2621
 
  if (table->getShare()->db_type() == heap_engine)
 
2615
  if (table->s->db_type() == heap_engine)
2622
2616
  {
2623
2617
    /*
2624
2618
      No blobs, otherwise it would have been MyISAM: set up a compare
2626
2620
    */
2627
2621
    qsort_cmp2 compare_key;
2628
2622
    void* cmp_arg;
2629
 
    Field **field= table->getFields();
2630
 
    Field **field_end= field + table->getShare()->sizeFields();
 
2623
    Field **field= table->field;
 
2624
    Field **field_end= field + table->s->fields;
2631
2625
    bool all_binary= true;
2632
2626
 
2633
2627
    for (tree_key_length= 0; field < field_end; ++field)
2648
2642
    }
2649
2643
    else
2650
2644
    {
2651
 
      if (table->getShare()->sizeFields() == 1)
 
2645
      if (table->s->fields == 1)
2652
2646
      {
2653
2647
        /*
2654
2648
          If we have only one field, which is the most common use of
2657
2651
          about other fields.
2658
2652
        */
2659
2653
        compare_key= (qsort_cmp2) simple_str_key_cmp;
2660
 
        cmp_arg= (void*) table->getField(0);
 
2654
        cmp_arg= (void*) table->field[0];
2661
2655
        /* tree_key_length has been set already */
2662
2656
      }
2663
2657
      else
2665
2659
        uint32_t *length;
2666
2660
        compare_key= (qsort_cmp2) composite_key_cmp;
2667
2661
        cmp_arg= (void*) this;
2668
 
        field_lengths= (uint32_t*) session->alloc(table->getShare()->sizeFields() * sizeof(uint32_t));
2669
 
        for (tree_key_length= 0, length= field_lengths, field= table->getFields();
 
2662
        field_lengths= (uint32_t*) session->alloc(table->s->fields * sizeof(uint32_t));
 
2663
        for (tree_key_length= 0, length= field_lengths, field= table->field;
2670
2664
             field < field_end; ++field, ++length)
2671
2665
        {
2672
2666
          *length= (*field)->pack_length();
2707
2701
  }
2708
2702
  else if (table)
2709
2703
  {
2710
 
    table->cursor->extra(HA_EXTRA_NO_CACHE);
2711
 
    table->cursor->ha_delete_all_rows();
2712
 
    table->cursor->extra(HA_EXTRA_WRITE_CACHE);
 
2704
    table->file->extra(HA_EXTRA_NO_CACHE);
 
2705
    table->file->ha_delete_all_rows();
 
2706
    table->file->extra(HA_EXTRA_WRITE_CACHE);
2713
2707
  }
2714
2708
}
2715
2709
 
2719
2713
  if (always_null)
2720
2714
    return 0;
2721
2715
  copy_fields(tmp_table_param);
2722
 
  if (copy_funcs(tmp_table_param->items_to_copy, table->in_use))
2723
 
    return true;
 
2716
  copy_funcs(tmp_table_param->items_to_copy);
2724
2717
 
2725
 
  for (Field **field= table->getFields() ; *field ; field++)
2726
 
  {
 
2718
  for (Field **field=table->field ; *field ; field++)
2727
2719
    if ((*field)->is_real_null(0))
2728
 
    {
2729
2720
      return 0;                                 // Don't count NULL
2730
 
    }
2731
 
  }
2732
2721
 
2733
2722
  is_evaluated= false;
2734
2723
  if (tree)
2739
2728
      bloat the tree without providing any valuable info. Besides,
2740
2729
      key_length used to initialize the tree didn't include space for them.
2741
2730
    */
2742
 
    return tree->unique_add(table->record[0] + table->getShare()->null_bytes);
 
2731
    return tree->unique_add(table->record[0] + table->s->null_bytes);
2743
2732
  }
2744
 
  if ((error= table->cursor->insertRecord(table->record[0])) &&
2745
 
      table->cursor->is_fatal_error(error, HA_CHECK_DUP))
 
2733
  if ((error= table->file->ha_write_row(table->record[0])) &&
 
2734
      table->file->is_fatal_error(error, HA_CHECK_DUP))
2746
2735
    return true;
2747
2736
  return false;
2748
2737
}
2767
2756
    return (int64_t) count;
2768
2757
  }
2769
2758
 
2770
 
  error= table->cursor->info(HA_STATUS_VARIABLE | HA_STATUS_NO_LOCK);
 
2759
  error= table->file->info(HA_STATUS_VARIABLE | HA_STATUS_NO_LOCK);
2771
2760
 
2772
2761
  if(error)
2773
2762
  {
2774
 
    table->print_error(error, MYF(0));
 
2763
    table->file->print_error(error, MYF(0));
2775
2764
  }
2776
2765
 
2777
 
  return table->cursor->stats.records;
 
2766
  return table->file->stats.records;
2778
2767
}
2779
2768
 
2780
2769
/*****************************************************************************
2828
2817
    */
2829
2818
    Field *field= item->get_tmp_table_field();
2830
2819
    int res;
2831
 
    uint32_t offset= field->offset(field->getTable()->record[0])-table->getShare()->null_bytes;
 
2820
    uint32_t offset= field->offset(field->table->record[0])-table->s->null_bytes;
2832
2821
    if((res= field->cmp((unsigned char*)key1 + offset, (unsigned char*)key2 + offset)))
2833
2822
      return res;
2834
2823
  }
2837
2826
 
2838
2827
 
2839
2828
/**
2840
 
  function of sort for syntax: GROUP_CONCAT(expr,... ORDER BY col,... )
 
2829
  function of sort for syntax: GROUP_CONCAT(expr,... order_st BY col,... )
2841
2830
*/
2842
2831
 
2843
2832
int group_concat_key_cmp_with_order(void* arg, const void* key1,
2844
2833
                                    const void* key2)
2845
2834
{
2846
2835
  Item_func_group_concat* grp_item= (Item_func_group_concat*) arg;
2847
 
  Order **order_item, **end;
 
2836
  order_st **order_item, **end;
2848
2837
  Table *table= grp_item->table;
2849
2838
 
2850
2839
  for (order_item= grp_item->order, end=order_item+ grp_item->arg_count_order;
2865
2854
    if (field && !item->const_item())
2866
2855
    {
2867
2856
      int res;
2868
 
      uint32_t offset= (field->offset(field->getTable()->record[0]) -
2869
 
                    table->getShare()->null_bytes);
 
2857
      uint32_t offset= (field->offset(field->table->record[0]) -
 
2858
                    table->s->null_bytes);
2870
2859
      if ((res= field->cmp((unsigned char*)key1 + offset, (unsigned char*)key2 + offset)))
2871
2860
        return (*order_item)->asc ? res : -res;
2872
2861
    }
2884
2873
  Append data from current leaf to item->result.
2885
2874
*/
2886
2875
 
2887
 
int dump_leaf_key(unsigned char* key, uint32_t ,
 
2876
int dump_leaf_key(unsigned char* key, element_count ,
2888
2877
                  Item_func_group_concat *item)
2889
2878
{
2890
2879
  Table *table= item->table;
2891
 
  String tmp((char *)table->getUpdateRecord(), table->getShare()->getRecordLength(),
 
2880
  String tmp((char *)table->record[1], table->s->reclength,
2892
2881
             default_charset_info);
2893
2882
  String tmp2;
2894
2883
  String *result= &item->result;
2915
2904
        because it contains both order and arg list fields.
2916
2905
      */
2917
2906
      Field *field= (*arg)->get_tmp_table_field();
2918
 
      uint32_t offset= (field->offset(field->getTable()->record[0]) -
2919
 
                    table->getShare()->null_bytes);
2920
 
      assert(offset < table->getShare()->getRecordLength());
2921
 
      res= field->val_str_internal(&tmp, key + offset);
 
2907
      uint32_t offset= (field->offset(field->table->record[0]) -
 
2908
                    table->s->null_bytes);
 
2909
      assert(offset < table->s->reclength);
 
2910
      res= field->val_str(&tmp, key + offset);
2922
2911
    }
2923
2912
    else
2924
2913
      res= (*arg)->val_str(&tmp);
2966
2955
                       bool distinct_arg, List<Item> *select_list,
2967
2956
                       SQL_LIST *order_list, String *separator_arg)
2968
2957
  :tmp_table_param(0), warning(0),
2969
 
   separator(separator_arg), tree(NULL), unique_filter(NULL), table(0),
 
2958
   separator(separator_arg), tree(0), unique_filter(NULL), table(0),
2970
2959
   order(0), context(context_arg),
2971
2960
   arg_count_order(order_list ? order_list->elements : 0),
2972
2961
   arg_count_field(select_list->elements),
2987
2976
           (for possible order items in temporare tables)
2988
2977
    order - arg_count_order
2989
2978
  */
2990
 
  if (!(args= (Item**) memory::sql_alloc(sizeof(Item*) * arg_count +
2991
 
                                 sizeof(Order*)*arg_count_order)))
 
2979
  if (!(args= (Item**) sql_alloc(sizeof(Item*) * arg_count +
 
2980
                                 sizeof(order_st*)*arg_count_order)))
2992
2981
    return;
2993
2982
 
2994
 
  order= (Order**)(args + arg_count);
 
2983
  order= (order_st**)(args + arg_count);
2995
2984
 
2996
2985
  /* fill args items of show and sort */
2997
2986
  List_iterator_fast<Item> li(*select_list);
3001
2990
 
3002
2991
  if (arg_count_order)
3003
2992
  {
3004
 
    Order **order_ptr= order;
3005
 
    for (Order *order_item= (Order*) order_list->first;
 
2993
    order_st **order_ptr= order;
 
2994
    for (order_st *order_item= (order_st*) order_list->first;
3006
2995
         order_item != NULL;
3007
2996
         order_item= order_item->next)
3008
2997
    {
3048
3037
  if (warning)
3049
3038
  {
3050
3039
    char warn_buff[DRIZZLE_ERRMSG_SIZE];
3051
 
    snprintf(warn_buff, sizeof(warn_buff), ER(ER_CUT_VALUE_GROUP_CONCAT), count_cut_values);
 
3040
    sprintf(warn_buff, ER(ER_CUT_VALUE_GROUP_CONCAT), count_cut_values);
3052
3041
    warning->set_msg(current_session, warn_buff);
3053
3042
    warning= 0;
3054
3043
  }
3064
3053
    if (table)
3065
3054
    {
3066
3055
      Session *session= table->in_use;
 
3056
      table->free_tmp_table(session);
3067
3057
      table= 0;
3068
3058
      if (tree)
3069
3059
      {
3078
3068
      if (warning)
3079
3069
      {
3080
3070
        char warn_buff[DRIZZLE_ERRMSG_SIZE];
3081
 
        snprintf(warn_buff, sizeof(warn_buff), ER(ER_CUT_VALUE_GROUP_CONCAT), count_cut_values);
 
3071
        sprintf(warn_buff, ER(ER_CUT_VALUE_GROUP_CONCAT), count_cut_values);
3082
3072
        warning->set_msg(session, warn_buff);
3083
3073
        warning= 0;
3084
3074
      }
3115
3105
  if (always_null)
3116
3106
    return 0;
3117
3107
  copy_fields(tmp_table_param);
3118
 
  if (copy_funcs(tmp_table_param->items_to_copy, table->in_use))
3119
 
    return true;
 
3108
  copy_funcs(tmp_table_param->items_to_copy);
3120
3109
 
3121
3110
  for (uint32_t i= 0; i < arg_count_field; i++)
3122
3111
  {
3136
3125
  {
3137
3126
    /* Filter out duplicate rows. */
3138
3127
    uint32_t count= unique_filter->elements_in_tree();
3139
 
    unique_filter->unique_add(table->record[0] + table->getShare()->null_bytes);
 
3128
    unique_filter->unique_add(table->record[0] + table->s->null_bytes);
3140
3129
    if (count == unique_filter->elements_in_tree())
3141
3130
      row_eligible= false;
3142
3131
  }
3143
3132
 
3144
3133
  TREE_ELEMENT *el= 0;                          // Only for safety
3145
3134
  if (row_eligible && tree)
3146
 
    el= tree_insert(tree, table->record[0] + table->getShare()->null_bytes, 0,
 
3135
    el= tree_insert(tree, table->record[0] + table->s->null_bytes, 0,
3147
3136
                    tree->custom_arg);
3148
3137
  /*
3149
3138
    If the row is not a duplicate (el->count == 1)
3152
3141
  */
3153
3142
  if (row_eligible && !warning_for_row &&
3154
3143
      (!tree || (el->count == 1 && distinct && !arg_count_order)))
3155
 
    dump_leaf_key(table->record[0] + table->getShare()->null_bytes, 1, this);
 
3144
    dump_leaf_key(table->record[0] + table->s->null_bytes, 1, this);
3156
3145
 
3157
3146
  return 0;
3158
3147
}
3193
3182
  null_value= 1;
3194
3183
  max_length= (size_t)session->variables.group_concat_max_len;
3195
3184
 
 
3185
  uint32_t offset;
 
3186
  if (separator->needs_conversion(separator->length(), separator->charset(),
 
3187
                                  collation.collation, &offset))
 
3188
  {
 
3189
    uint32_t buflen= collation.collation->mbmaxlen * separator->length();
 
3190
    uint32_t errors, conv_length;
 
3191
    char *buf;
 
3192
    String *new_separator;
 
3193
 
 
3194
    if (!(buf= (char*) session->alloc(buflen)) ||
 
3195
        !(new_separator= new(session->mem_root)
 
3196
                           String(buf, buflen, collation.collation)))
 
3197
      return true;
 
3198
 
 
3199
    conv_length= copy_and_convert(buf, buflen, collation.collation,
 
3200
                                  separator->ptr(), separator->length(),
 
3201
                                  separator->charset(), &errors);
 
3202
    new_separator->length(conv_length);
 
3203
    separator= new_separator;
 
3204
  }
 
3205
 
3196
3206
  if (check_sum_func(session, ref))
3197
3207
    return true;
3198
3208
 
3254
3264
  {
3255
3265
    /*
3256
3266
      Currently we have to force conversion of BLOB values to VARCHAR's
3257
 
      if we are to store them in TREE objects used for ORDER BY and
 
3267
      if we are to store them in TREE objects used for order_st BY and
3258
3268
      DISTINCT. This leads to truncation if the BLOB's size exceeds
3259
3269
      Field_varstring::MAX_SIZE.
3260
3270
    */
3266
3276
    We have to create a temporary table to get descriptions of fields
3267
3277
    (types, sizes and so on).
3268
3278
 
3269
 
    Note that in the table, we first have the ORDER BY fields, then the
 
3279
    Note that in the table, we first have the order_st BY fields, then the
3270
3280
    field list.
3271
3281
  */
3272
3282
  if (!(table= create_tmp_table(session, tmp_table_param, all_fields,
3273
 
                                (Order*) 0, 0, true,
 
3283
                                (order_st*) 0, 0, true,
3274
3284
                                (select_lex->options | session->options),
3275
3285
                                HA_POS_ERROR, (char*) "")))
3276
 
  {
3277
3286
    return(true);
3278
 
  }
3279
 
 
3280
 
  table->cursor->extra(HA_EXTRA_NO_ROWS);
 
3287
  table->file->extra(HA_EXTRA_NO_ROWS);
3281
3288
  table->no_rows= 1;
3282
3289
 
3283
3290
  /*
3285
3292
     Don't reserve space for NULLs: if any of gconcat arguments is NULL,
3286
3293
     the row is not added to the result.
3287
3294
  */
3288
 
  uint32_t tree_key_length= table->getShare()->getRecordLength() - table->getShare()->null_bytes;
 
3295
  uint32_t tree_key_length= table->s->reclength - table->s->null_bytes;
3289
3296
 
3290
3297
  if (arg_count_order)
3291
3298
  {
3292
3299
    tree= &tree_base;
3293
3300
    /*
3294
3301
      Create a tree for sorting. The tree is used to sort (according to the
3295
 
      syntax of this function). If there is no ORDER BY clause, we don't
 
3302
      syntax of this function). If there is no order_st BY clause, we don't
3296
3303
      create this tree.
3297
3304
    */
3298
 
    init_tree(tree, (uint32_t) min(session->variables.max_heap_table_size,
3299
 
                                   (uint64_t)(session->variables.sortbuff_size/16)), 
3300
 
              0,
 
3305
    init_tree(tree, (uint32_t) cmin(session->variables.max_heap_table_size,
 
3306
                               session->variables.sortbuff_size/16), 0,
3301
3307
              tree_key_length,
3302
 
              group_concat_key_cmp_with_order , false, NULL, (void*) this);
 
3308
              group_concat_key_cmp_with_order , 0, NULL, (void*) this);
3303
3309
  }
3304
3310
 
3305
3311
  if (distinct)
3323
3329
  tree= 0;
3324
3330
}
3325
3331
 
3326
 
double Item_func_group_concat::val_real()
3327
 
{
3328
 
  String *res;  res=val_str(&str_value);
3329
 
  return res ? internal::my_atof(res->c_ptr()) : 0.0;
3330
 
}
3331
 
 
3332
 
int64_t Item_func_group_concat::val_int()
3333
 
{
3334
 
  String *res;
3335
 
  char *end_ptr;
3336
 
  int error;
3337
 
  if (!(res= val_str(&str_value)))
3338
 
    return (int64_t) 0;
3339
 
  end_ptr= (char*) res->ptr()+ res->length();
3340
 
  return internal::my_strtoll10(res->ptr(), &end_ptr, &error);
3341
 
}
3342
3332
 
3343
3333
String* Item_func_group_concat::val_str(String* )
3344
3334
{
3400
3390
  if (!original && unique_filter)
3401
3391
    delete unique_filter;
3402
3392
}
3403
 
 
3404
 
} /* namespace drizzled */