~drizzle-trunk/drizzle/development

« back to all changes in this revision

Viewing changes to drizzled/field/varstring.cc

Moved sql_common.h and my_time.h to libdrizzle.

Show diffs side-by-side

added added

removed removed

Lines of Context:
1
 
/* - mode: c++ c-basic-offset: 2; indent-tabs-mode: nil; -*-
 
1
/* - mode: c; c-basic-offset: 2; indent-tabs-mode: nil; -*-
2
2
 *  vim:expandtab:shiftwidth=2:tabstop=2:smarttab:
3
3
 *
4
4
 *  Copyright (C) 2008 MySQL
18
18
 *  Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
19
19
 */
20
20
 
 
21
#ifdef USE_PRAGMA_IMPLEMENTATION
 
22
#pragma implementation                          // gcc: Class implementation
 
23
#endif
21
24
 
22
 
#include <drizzled/server_includes.h>
23
25
#include <drizzled/field/varstring.h>
24
26
 
25
27
/****************************************************************************
38
40
  is 2.
39
41
****************************************************************************/
40
42
 
41
 
const uint32_t Field_varstring::MAX_SIZE= UINT16_MAX;
 
43
const uint Field_varstring::MAX_SIZE= UINT16_MAX;
42
44
 
43
45
/**
44
46
   Save the field metadata for varstring fields.
51
53
 
52
54
   @returns number of bytes written to metadata_ptr
53
55
*/
54
 
int Field_varstring::do_save_field_metadata(unsigned char *metadata_ptr)
 
56
int Field_varstring::do_save_field_metadata(uchar *metadata_ptr)
55
57
{
56
58
  char *ptr= (char *)metadata_ptr;
57
59
  assert(field_length <= 65535);
59
61
  return 2;
60
62
}
61
63
 
62
 
int Field_varstring::store(const char *from,uint32_t length, const CHARSET_INFO * const cs)
 
64
int Field_varstring::store(const char *from,uint length,CHARSET_INFO *cs)
63
65
{
64
 
  uint32_t copy_length;
 
66
  uint copy_length;
65
67
  const char *well_formed_error_pos;
66
68
  const char *cannot_convert_error_pos;
67
69
  const char *from_end_pos;
76
78
                                       &from_end_pos);
77
79
 
78
80
  if (length_bytes == 1)
79
 
    *ptr= (unsigned char) copy_length;
 
81
    *ptr= (uchar) copy_length;
80
82
  else
81
83
    int2store(ptr, copy_length);
82
84
 
91
93
int Field_varstring::store(int64_t nr, bool unsigned_val)
92
94
{
93
95
  char buff[64];
94
 
  uint32_t  length;
 
96
  uint  length;
95
97
  length= (uint) (field_charset->cset->int64_t10_to_str)(field_charset,
96
98
                                                          buff,
97
99
                                                          sizeof(buff),
106
108
{
107
109
  int not_used;
108
110
  char *end_not_used;
109
 
  uint32_t length= length_bytes == 1 ? (uint) *ptr : uint2korr(ptr);
 
111
  uint length= length_bytes == 1 ? (uint) *ptr : uint2korr(ptr);
110
112
  return my_strntod(field_charset, (char*) ptr+length_bytes, length,
111
113
                    &end_not_used, &not_used);
112
114
}
116
118
{
117
119
  int not_used;
118
120
  char *end_not_used;
119
 
  uint32_t length= length_bytes == 1 ? (uint) *ptr : uint2korr(ptr);
 
121
  uint length= length_bytes == 1 ? (uint) *ptr : uint2korr(ptr);
120
122
  return my_strntoll(field_charset, (char*) ptr+length_bytes, length, 10,
121
123
                     &end_not_used, &not_used);
122
124
}
124
126
String *Field_varstring::val_str(String *val_buffer __attribute__((unused)),
125
127
                                 String *val_ptr)
126
128
{
127
 
  uint32_t length=  length_bytes == 1 ? (uint) *ptr : uint2korr(ptr);
 
129
  uint length=  length_bytes == 1 ? (uint) *ptr : uint2korr(ptr);
128
130
  val_ptr->set((const char*) ptr+length_bytes, length, field_charset);
129
131
  return val_ptr;
130
132
}
132
134
 
133
135
my_decimal *Field_varstring::val_decimal(my_decimal *decimal_value)
134
136
{
135
 
  uint32_t length= length_bytes == 1 ? (uint) *ptr : uint2korr(ptr);
 
137
  uint length= length_bytes == 1 ? (uint) *ptr : uint2korr(ptr);
136
138
  str2my_decimal(E_DEC_FATAL_ERROR, (char*) ptr+length_bytes, length,
137
139
                 charset(), decimal_value);
138
140
  return decimal_value;
139
141
}
140
142
 
141
143
 
142
 
int Field_varstring::cmp_max(const unsigned char *a_ptr, const unsigned char *b_ptr,
143
 
                             uint32_t max_len)
 
144
int Field_varstring::cmp_max(const uchar *a_ptr, const uchar *b_ptr,
 
145
                             uint max_len)
144
146
{
145
 
  uint32_t a_length, b_length;
 
147
  uint a_length, b_length;
146
148
  int diff;
147
149
 
148
150
  if (length_bytes == 1)
173
175
    varstring and blob keys are ALWAYS stored with a 2 byte length prefix
174
176
*/
175
177
 
176
 
int Field_varstring::key_cmp(const unsigned char *key_ptr, uint32_t max_key_length)
 
178
int Field_varstring::key_cmp(const uchar *key_ptr, uint max_key_length)
177
179
{
178
 
  uint32_t length=  length_bytes == 1 ? (uint) *ptr : uint2korr(ptr);
179
 
  uint32_t local_char_length= max_key_length / field_charset->mbmaxlen;
 
180
  uint length=  length_bytes == 1 ? (uint) *ptr : uint2korr(ptr);
 
181
  uint local_char_length= max_key_length / field_charset->mbmaxlen;
180
182
 
181
183
  local_char_length= my_charpos(field_charset, ptr + length_bytes,
182
184
                          ptr + length_bytes + length, local_char_length);
198
200
    (keys are created and compared in key.cc)
199
201
*/
200
202
 
201
 
int Field_varstring::key_cmp(const unsigned char *a,const unsigned char *b)
 
203
int Field_varstring::key_cmp(const uchar *a,const uchar *b)
202
204
{
203
205
  return field_charset->coll->strnncollsp(field_charset,
204
206
                                          a + HA_KEY_BLOB_LENGTH,
209
211
}
210
212
 
211
213
 
212
 
void Field_varstring::sort_string(unsigned char *to,uint32_t length)
 
214
void Field_varstring::sort_string(uchar *to,uint length)
213
215
{
214
 
  uint32_t tot_length=  length_bytes == 1 ? (uint) *ptr : uint2korr(ptr);
 
216
  uint tot_length=  length_bytes == 1 ? (uint) *ptr : uint2korr(ptr);
215
217
 
216
218
  if (field_charset == &my_charset_bin)
217
219
  {
244
246
 
245
247
void Field_varstring::sql_type(String &res) const
246
248
{
247
 
  const CHARSET_INFO * const cs=res.charset();
248
 
  uint32_t length;
 
249
  THD *thd= table->in_use;
 
250
  CHARSET_INFO *cs=res.charset();
 
251
  ulong length;
249
252
 
250
253
  length= cs->cset->snprintf(cs,(char*) res.ptr(),
251
254
                             res.alloced_length(), "%s(%d)",
252
255
                              (has_charset() ? "varchar" : "varbinary"),
253
256
                             (int) field_length / charset()->mbmaxlen);
254
257
  res.length(length);
 
258
  if ((thd->variables.sql_mode & (MODE_MYSQL323 | MODE_MYSQL40)) &&
 
259
      has_charset() && (charset()->state & MY_CS_BINSORT))
 
260
    res.append(STRING_WITH_LEN(" binary"));
255
261
}
256
262
 
257
263
 
262
268
 
263
269
uint32_t Field_varstring::used_length()
264
270
{
265
 
  return length_bytes == 1 ? 1 + (uint32_t) (unsigned char) *ptr : 2 + uint2korr(ptr);
 
271
  return length_bytes == 1 ? 1 + (uint32_t) (uchar) *ptr : 2 + uint2korr(ptr);
266
272
}
267
273
 
268
274
/*
270
276
  Here the number of length bytes are depending on the given max_length
271
277
*/
272
278
 
273
 
unsigned char *Field_varstring::pack(unsigned char *to, const unsigned char *from,
274
 
                             uint32_t max_length,
 
279
uchar *Field_varstring::pack(uchar *to, const uchar *from,
 
280
                             uint max_length,
275
281
                             bool low_byte_first __attribute__((unused)))
276
282
{
277
 
  uint32_t length= length_bytes == 1 ? (uint) *from : uint2korr(from);
 
283
  uint length= length_bytes == 1 ? (uint) *from : uint2korr(from);
278
284
  set_if_smaller(max_length, field_length);
279
285
  if (length > max_length)
280
286
    length=max_length;
291
297
}
292
298
 
293
299
 
294
 
unsigned char *
295
 
Field_varstring::pack_key(unsigned char *to, const unsigned char *key, uint32_t max_length,
 
300
uchar *
 
301
Field_varstring::pack_key(uchar *to, const uchar *key, uint max_length,
296
302
                          bool low_byte_first __attribute__((unused)))
297
303
{
298
 
  uint32_t length=  length_bytes == 1 ? (uint) *key : uint2korr(key);
299
 
  uint32_t local_char_length= ((field_charset->mbmaxlen > 1) ?
 
304
  uint length=  length_bytes == 1 ? (uint) *key : uint2korr(key);
 
305
  uint local_char_length= ((field_charset->mbmaxlen > 1) ?
300
306
                     max_length/field_charset->mbmaxlen : max_length);
301
307
  key+= length_bytes;
302
308
  if (length > local_char_length)
329
335
    Pointer to end of 'key' (To the next key part if multi-segment key)
330
336
*/
331
337
 
332
 
const unsigned char *
333
 
Field_varstring::unpack_key(unsigned char *to __attribute__((unused)),
334
 
                            const unsigned char *key, uint32_t max_length,
 
338
const uchar *
 
339
Field_varstring::unpack_key(uchar *to __attribute__((unused)),
 
340
                            const uchar *key, uint max_length,
335
341
                            bool low_byte_first __attribute__((unused)))
336
342
{
337
343
  /* get length of the blob key */
341
347
 
342
348
  /* put the length into the record buffer */
343
349
  if (length_bytes == 1)
344
 
    *ptr= (unsigned char) length;
 
350
    *ptr= (uchar) length;
345
351
  else
346
352
    int2store(ptr, length);
347
353
  memcpy(ptr + length_bytes, key, length);
359
365
    end of key storage
360
366
*/
361
367
 
362
 
unsigned char *
363
 
Field_varstring::pack_key_from_key_image(unsigned char *to, const unsigned char *from, uint32_t max_length,
 
368
uchar *
 
369
Field_varstring::pack_key_from_key_image(uchar *to, const uchar *from, uint max_length,
364
370
                                         bool low_byte_first __attribute__((unused)))
365
371
{
366
372
  /* Key length is always stored as 2 bytes */
367
 
  uint32_t length= uint2korr(from);
 
373
  uint length= uint2korr(from);
368
374
  if (length > max_length)
369
375
    length= max_length;
370
376
  *to++= (char) (length & 255);
391
397
 
392
398
   @return  New pointer into memory based on from + length of the data
393
399
*/
394
 
const unsigned char *
395
 
Field_varstring::unpack(unsigned char *to, const unsigned char *from,
396
 
                        uint32_t param_data,
 
400
const uchar *
 
401
Field_varstring::unpack(uchar *to, const uchar *from,
 
402
                        uint param_data,
397
403
                        bool low_byte_first __attribute__((unused)))
398
404
{
399
 
  uint32_t length;
400
 
  uint32_t l_bytes= (param_data && (param_data < field_length)) ? 
 
405
  uint length;
 
406
  uint l_bytes= (param_data && (param_data < field_length)) ? 
401
407
                (param_data <= 255) ? 1 : 2 : length_bytes;
402
408
  if (l_bytes == 1)
403
409
  {
418
424
}
419
425
 
420
426
 
421
 
int Field_varstring::pack_cmp(const unsigned char *a, const unsigned char *b,
422
 
                              uint32_t key_length_arg,
423
 
                              bool insert_or_update)
 
427
int Field_varstring::pack_cmp(const uchar *a, const uchar *b,
 
428
                              uint key_length_arg,
 
429
                              my_bool insert_or_update)
424
430
{
425
 
  uint32_t a_length, b_length;
 
431
  uint a_length, b_length;
426
432
  if (key_length_arg > 255)
427
433
  {
428
434
    a_length=uint2korr(a); a+= 2;
440
446
}
441
447
 
442
448
 
443
 
int Field_varstring::pack_cmp(const unsigned char *b, uint32_t key_length_arg,
444
 
                              bool insert_or_update)
 
449
int Field_varstring::pack_cmp(const uchar *b, uint key_length_arg,
 
450
                              my_bool insert_or_update)
445
451
{
446
 
  unsigned char *a= ptr+ length_bytes;
447
 
  uint32_t a_length=  length_bytes == 1 ? (uint) *ptr : uint2korr(ptr);
448
 
  uint32_t b_length;
449
 
  uint32_t local_char_length= ((field_charset->mbmaxlen > 1) ?
 
452
  uchar *a= ptr+ length_bytes;
 
453
  uint a_length=  length_bytes == 1 ? (uint) *ptr : uint2korr(ptr);
 
454
  uint b_length;
 
455
  uint local_char_length= ((field_charset->mbmaxlen > 1) ?
450
456
                           key_length_arg / field_charset->mbmaxlen :
451
457
                           key_length_arg);
452
458
 
471
477
}
472
478
 
473
479
 
474
 
uint32_t Field_varstring::packed_col_length(const unsigned char *data_ptr, uint32_t length)
 
480
uint Field_varstring::packed_col_length(const uchar *data_ptr, uint length)
475
481
{
476
482
  if (length > 255)
477
483
    return uint2korr(data_ptr)+2;
479
485
}
480
486
 
481
487
 
482
 
uint32_t Field_varstring::max_packed_col_length(uint32_t max_length)
 
488
uint Field_varstring::max_packed_col_length(uint max_length)
483
489
{
484
490
  return (max_length > 255 ? 2 : 1)+max_length;
485
491
}
486
492
 
487
 
uint32_t Field_varstring::get_key_image(unsigned char *buff,
488
 
                                    uint32_t length,
 
493
uint Field_varstring::get_key_image(uchar *buff,
 
494
                                    uint length,
489
495
                                    imagetype type __attribute__((unused)))
490
496
{
491
 
  uint32_t f_length=  length_bytes == 1 ? (uint) *ptr : uint2korr(ptr);
492
 
  uint32_t local_char_length= length / field_charset->mbmaxlen;
493
 
  unsigned char *pos= ptr+length_bytes;
 
497
  uint f_length=  length_bytes == 1 ? (uint) *ptr : uint2korr(ptr);
 
498
  uint local_char_length= length / field_charset->mbmaxlen;
 
499
  uchar *pos= ptr+length_bytes;
494
500
  local_char_length= my_charpos(field_charset, pos, pos + f_length,
495
501
                                local_char_length);
496
502
  set_if_smaller(f_length, local_char_length);
503
509
      Must clear this as we do a memcmp in opt_range.cc to detect
504
510
      identical keys
505
511
    */
506
 
    memset(buff+HA_KEY_BLOB_LENGTH+f_length, 0, (length-f_length));
 
512
    bzero(buff+HA_KEY_BLOB_LENGTH+f_length, (length-f_length));
507
513
  }
508
514
  return HA_KEY_BLOB_LENGTH+f_length;
509
515
}
510
516
 
511
517
 
512
 
void Field_varstring::set_key_image(const unsigned char *buff,uint32_t length)
 
518
void Field_varstring::set_key_image(const uchar *buff,uint length)
513
519
{
514
520
  length= uint2korr(buff);                      // Real length is here
515
521
  (void) Field_varstring::store((const char*) buff+HA_KEY_BLOB_LENGTH, length,
517
523
}
518
524
 
519
525
 
520
 
int Field_varstring::cmp_binary(const unsigned char *a_ptr, const unsigned char *b_ptr,
 
526
int Field_varstring::cmp_binary(const uchar *a_ptr, const uchar *b_ptr,
521
527
                                uint32_t max_length)
522
528
{
523
529
  uint32_t a_length,b_length;
540
546
}
541
547
 
542
548
 
543
 
Field *Field_varstring::new_field(MEM_ROOT *root, Table *new_table, bool keep_type)
 
549
Field *Field_varstring::new_field(MEM_ROOT *root, struct st_table *new_table,
 
550
                                  bool keep_type)
544
551
{
545
552
  Field_varstring *res= (Field_varstring*) Field::new_field(root, new_table,
546
553
                                                            keep_type);
551
558
 
552
559
 
553
560
Field *Field_varstring::new_key_field(MEM_ROOT *root,
554
 
                                      Table *new_table,
555
 
                                      unsigned char *new_ptr, unsigned char *new_null_ptr,
556
 
                                      uint32_t new_null_bit)
 
561
                                      struct st_table *new_table,
 
562
                                      uchar *new_ptr, uchar *new_null_ptr,
 
563
                                      uint new_null_bit)
557
564
{
558
565
  Field_varstring *res;
559
566
  if ((res= (Field_varstring*) Field::new_key_field(root,
569
576
}
570
577
 
571
578
 
572
 
uint32_t Field_varstring::is_equal(Create_field *new_field)
 
579
uint Field_varstring::is_equal(Create_field *new_field)
573
580
{
574
581
  if (new_field->sql_type == real_type() &&
575
582
      new_field->charset == field_charset)
585
592
}
586
593
 
587
594
 
588
 
void Field_varstring::hash(uint32_t *nr, uint32_t *nr2)
 
595
void Field_varstring::hash(ulong *nr, ulong *nr2)
589
596
{
590
597
  if (is_null())
591
598
  {
593
600
  }
594
601
  else
595
602
  {
596
 
    uint32_t len=  length_bytes == 1 ? (uint) *ptr : uint2korr(ptr);
597
 
    const CHARSET_INFO * const cs= charset();
 
603
    uint len=  length_bytes == 1 ? (uint) *ptr : uint2korr(ptr);
 
604
    CHARSET_INFO *cs= charset();
598
605
    cs->coll->hash_sort(cs, ptr + length_bytes, len, nr, nr2);
599
606
  }
600
607
}