18
18
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
21
#ifdef USE_PRAGMA_IMPLEMENTATION
22
#pragma implementation // gcc: Class implementation
25
22
#include <drizzled/server_includes.h>
26
23
#include <drizzled/field/blob.h>
28
#define BLOB_PACK_LENGTH_TO_MAX_LENGH(arg) \
29
((uint32_t) ((1LL << min(arg, (uint)4) * 8) - 1LL))
24
#include <drizzled/table.h>
25
#include <drizzled/session.h>
32
blob_pack_length_to_max_length(uint32_t arg)
34
return (INT64_C(1) << cmin(arg, 4U) * 8) - INT64_C(1);
31
38
/****************************************************************************
34
41
** packlength slot and may be from 1-4.
35
42
****************************************************************************/
37
Field_blob::Field_blob(uchar *ptr_arg, uchar *null_ptr_arg, uchar null_bit_arg,
44
Field_blob::Field_blob(unsigned char *ptr_arg, unsigned char *null_ptr_arg, unsigned char null_bit_arg,
38
45
enum utype unireg_check_arg, const char *field_name_arg,
39
TABLE_SHARE *share, uint blob_pack_length,
46
TABLE_SHARE *share, uint32_t blob_pack_length,
40
47
const CHARSET_INFO * const cs)
41
:Field_longstr(ptr_arg, BLOB_PACK_LENGTH_TO_MAX_LENGH(blob_pack_length),
48
:Field_longstr(ptr_arg, blob_pack_length_to_max_length(blob_pack_length),
42
49
null_ptr_arg, null_bit_arg, unireg_check_arg, field_name_arg,
44
51
packlength(blob_pack_length)
52
void Field_blob::store_length(uchar *i_ptr,
59
void Field_blob::store_length(unsigned char *i_ptr,
60
uint32_t i_packlength,
55
62
bool low_byte_first __attribute__((unused)))
57
64
switch (i_packlength) {
59
i_ptr[0]= (uchar) i_number;
66
i_ptr[0]= (unsigned char) i_number;
62
69
#ifdef WORDS_BIGENDIAN
87
uint32_t Field_blob::get_length(const uchar *pos,
94
void Field_blob::store_length(unsigned char *i_ptr, uint32_t i_packlength,
97
store_length(i_ptr, i_packlength, i_number, table->s->db_low_byte_first);
101
uint32_t Field_blob::get_length(const unsigned char *pos,
102
uint32_t packlength_arg,
89
103
bool low_byte_first __attribute__((unused)))
91
105
switch (packlength_arg) {
137
uint32_t Field_blob::get_packed_size(const unsigned char *ptr_arg,
140
return packlength + get_length(ptr_arg, packlength, low_byte_first);
144
uint32_t Field_blob::get_length(uint32_t row_offset)
146
return get_length(ptr+row_offset, this->packlength,
147
table->s->db_low_byte_first);
151
uint32_t Field_blob::get_length(const unsigned char *ptr_arg)
153
return get_length(ptr_arg, this->packlength, table->s->db_low_byte_first);
124
158
Put a blob length field into a record buffer.
153
int Field_blob::store(const char *from,uint length, const CHARSET_INFO * const cs)
187
int Field_blob::store(const char *from,uint32_t length, const CHARSET_INFO * const cs)
155
uint copy_length, new_length;
189
uint32_t copy_length, new_length;
156
190
const char *well_formed_error_pos;
157
191
const char *cannot_convert_error_pos;
158
192
const char *from_end_pos, *tmp;
171
205
if (!String::needs_conversion(length, cs, field_charset, &dummy_offset))
173
207
Field_blob::store_length(length);
174
memcpy(ptr+packlength, &from, sizeof(char*));
208
memmove(ptr+packlength, &from, sizeof(char*));
177
211
if (tmpstr.copy(from, length, cs))
192
226
Field_blob::store_length(copy_length);
193
227
tmp= value.ptr();
194
memcpy(ptr + packlength, &tmp, sizeof(char*));
228
memmove(ptr + packlength, &tmp, sizeof(char*));
210
244
Field_blob::store_length(copy_length);
211
245
tmp= value.ptr();
212
memcpy(ptr+packlength, &tmp, sizeof(char*));
246
memmove(ptr+packlength, &tmp, sizeof(char*));
214
248
if (check_string_copy_error(this, well_formed_error_pos,
215
249
cannot_convert_error_pos, from + length, cs))
302
int Field_blob::cmp(const uchar *a,uint32_t a_length, const uchar *b,
336
int Field_blob::cmp(const unsigned char *a,uint32_t a_length, const unsigned char *b,
303
337
uint32_t b_length)
305
return field_charset->coll->strnncollsp(field_charset,
339
return field_charset->coll->strnncollsp(field_charset,
306
340
a, a_length, b, b_length,
311
int Field_blob::cmp_max(const uchar *a_ptr, const uchar *b_ptr,
345
int Field_blob::cmp_max(const unsigned char *a_ptr, const unsigned char *b_ptr,
348
unsigned char *blob1,*blob2;
315
349
memcpy(&blob1,a_ptr+packlength,sizeof(char*));
316
350
memcpy(&blob2,b_ptr+packlength,sizeof(char*));
317
uint a_len= get_length(a_ptr), b_len= get_length(b_ptr);
351
uint32_t a_len= get_length(a_ptr), b_len= get_length(b_ptr);
318
352
set_if_smaller(a_len, max_length);
319
353
set_if_smaller(b_len, max_length);
320
354
return Field_blob::cmp(blob1,a_len,blob2,b_len);
324
int Field_blob::cmp_binary(const uchar *a_ptr, const uchar *b_ptr,
358
int Field_blob::cmp_binary(const unsigned char *a_ptr, const unsigned char *b_ptr,
325
359
uint32_t max_length)
329
363
uint32_t a_length,b_length;
330
364
memcpy(&a,a_ptr+packlength,sizeof(char*));
331
365
memcpy(&b,b_ptr+packlength,sizeof(char*));
335
369
b_length=get_length(b_ptr);
336
370
if (b_length > max_length)
337
371
b_length=max_length;
338
diff=memcmp(a,b,min(a_length,b_length));
372
diff=memcmp(a,b,cmin(a_length,b_length));
339
373
return diff ? diff : (int) (a_length - b_length);
343
377
/* The following is used only when comparing a key */
345
uint Field_blob::get_key_image(uchar *buff,
347
imagetype type_arg __attribute__((unused)))
379
uint32_t Field_blob::get_key_image(unsigned char *buff,
349
383
uint32_t blob_length= get_length(ptr);
353
uint local_char_length= length / field_charset->mbmaxlen;
387
uint32_t local_char_length= length / field_charset->mbmaxlen;
354
388
local_char_length= my_charpos(field_charset, blob, blob + blob_length,
355
389
local_char_length);
356
390
set_if_smaller(blob_length, local_char_length);
373
void Field_blob::set_key_image(const uchar *buff,uint length)
407
uint32_t Field_blob::get_key_image(basic_string<unsigned char> &buff,
411
uint32_t blob_length= get_length(ptr);
415
uint32_t local_char_length= length / field_charset->mbmaxlen;
416
local_char_length= my_charpos(field_charset, blob, blob + blob_length,
418
set_if_smaller(blob_length, local_char_length);
420
unsigned char len_buff[HA_KEY_BLOB_LENGTH];
421
int2store(len_buff,length);
422
buff.append(len_buff);
423
buff.append(blob, blob_length);
425
if (length > blob_length)
428
Must clear this as we do a memcmp in opt_range.cc to detect
432
buff.append(length-blob_length, '0');
434
return HA_KEY_BLOB_LENGTH+length;
438
void Field_blob::set_key_image(const unsigned char *buff,uint32_t length)
375
440
length= uint2korr(buff);
376
441
(void) Field_blob::store((const char*) buff+HA_KEY_BLOB_LENGTH, length,
381
int Field_blob::key_cmp(const uchar *key_ptr, uint max_key_length)
446
int Field_blob::key_cmp(const unsigned char *key_ptr, uint32_t max_key_length)
384
uint blob_length=get_length(ptr);
448
unsigned char *blob1;
449
uint32_t blob_length=get_length(ptr);
385
450
memcpy(&blob1,ptr+packlength,sizeof(char*));
386
451
const CHARSET_INFO * const cs= charset();
387
uint local_char_length= max_key_length / cs->mbmaxlen;
452
uint32_t local_char_length= max_key_length / cs->mbmaxlen;
388
453
local_char_length= my_charpos(cs, blob1, blob1+blob_length,
389
454
local_char_length);
390
455
set_if_smaller(blob_length, local_char_length);
393
458
uint2korr(key_ptr));
396
int Field_blob::key_cmp(const uchar *a,const uchar *b)
461
int Field_blob::key_cmp(const unsigned char *a,const unsigned char *b)
398
463
return Field_blob::cmp(a+HA_KEY_BLOB_LENGTH, uint2korr(a),
399
464
b+HA_KEY_BLOB_LENGTH, uint2korr(b));
411
476
@returns number of bytes written to metadata_ptr
413
int Field_blob::do_save_field_metadata(uchar *metadata_ptr)
478
int Field_blob::do_save_field_metadata(unsigned char *metadata_ptr)
415
480
*metadata_ptr= pack_length_no_ptr();
420
485
uint32_t Field_blob::sort_length() const
422
return (uint32_t) (current_thd->variables.max_sort_length +
487
return (uint32_t) (current_session->variables.max_sort_length +
423
488
(field_charset == &my_charset_bin ? 0 : packlength));
427
void Field_blob::sort_string(uchar *to,uint length)
492
void Field_blob::sort_string(unsigned char *to,uint32_t length)
430
uint blob_length=get_length();
495
uint32_t blob_length=get_length();
432
497
if (!blob_length)
433
498
memset(to, 0, length);
461
526
memcpy(&blob,ptr+packlength,sizeof(char*));
463
528
blob_length=my_strnxfrm(field_charset,
464
529
to, length, blob, blob_length);
465
530
assert(blob_length == length);
475
546
res.set_ascii(STRING_WITH_LEN("text"));
478
uchar *Field_blob::pack(uchar *to, const uchar *from,
479
uint max_length, bool low_byte_first)
549
unsigned char *Field_blob::pack(unsigned char *to, const unsigned char *from,
550
uint32_t max_length, bool low_byte_first)
552
unsigned char *save= ptr;
553
ptr= (unsigned char*) from;
483
554
uint32_t length=get_length(); // Length of from string
487
558
length given is smaller than the actual length of the blob, we
488
559
just store the initial bytes of the blob.
490
store_length(to, packlength, min(length, max_length), low_byte_first);
561
store_length(to, packlength, cmin(length, max_length), low_byte_first);
493
564
Store the actual blob data, which will occupy 'length' bytes.
497
get_ptr((uchar**) &from);
568
get_ptr((unsigned char**) &from);
498
569
memcpy(to+packlength, from,length);
500
571
ptr=save; // Restore org row pointer
506
577
Unpack a blob field from row data.
508
This method is used to unpack a blob field from a master whose size of
579
This method is used to unpack a blob field from a master whose size of
509
580
the field is less than that of the slave. Note: This method is included
510
581
to satisfy inheritance rules, but is not needed for blob fields. It
511
582
simply is used as a pass-through to the original unpack() method for
520
591
@return New pointer into memory based on from + length of the data
522
const uchar *Field_blob::unpack(uchar *to __attribute__((unused)),
593
const unsigned char *Field_blob::unpack(unsigned char *to __attribute__((unused)),
594
const unsigned char *from,
525
596
bool low_byte_first)
527
uint const master_packlength=
598
uint32_t const master_packlength=
528
599
param_data > 0 ? param_data & 0xFF : packlength;
529
600
uint32_t const length= get_length(from, master_packlength, low_byte_first);
530
601
bitmap_set_bit(table->write_set, field_index);
536
607
/* Keys for blobs are like keys on varchars */
538
int Field_blob::pack_cmp(const uchar *a, const uchar *b, uint key_length_arg,
609
int Field_blob::pack_cmp(const unsigned char *a, const unsigned char *b, uint32_t key_length_arg,
539
610
bool insert_or_update)
541
uint a_length, b_length;
612
uint32_t a_length, b_length;
542
613
if (key_length_arg > 255)
544
615
a_length=uint2korr(a); a+=2;
559
int Field_blob::pack_cmp(const uchar *b, uint key_length_arg,
630
int Field_blob::pack_cmp(const unsigned char *b, uint32_t key_length_arg,
560
631
bool insert_or_update)
563
uint a_length, b_length;
634
uint32_t a_length, b_length;
564
635
memcpy(&a,ptr+packlength,sizeof(char*));
566
637
return key_length_arg > 0 ? -1 : 0;
581
652
/** Create a packed key that will be used for storage from a MySQL row. */
584
Field_blob::pack_key(uchar *to, const uchar *from, uint max_length,
655
Field_blob::pack_key(unsigned char *to, const unsigned char *from, uint32_t max_length,
585
656
bool low_byte_first __attribute__((unused)))
658
unsigned char *save= ptr;
659
ptr= (unsigned char*) from;
589
660
uint32_t length=get_length(); // Length of from string
590
uint local_char_length= ((field_charset->mbmaxlen > 1) ?
661
uint32_t local_char_length= ((field_charset->mbmaxlen > 1) ?
591
662
max_length/field_charset->mbmaxlen : max_length);
593
get_ptr((uchar**) &from);
664
get_ptr((unsigned char**) &from);
594
665
if (length > local_char_length)
595
666
local_char_length= my_charpos(field_charset, from, from+length,
596
667
local_char_length);
597
668
set_if_smaller(length, local_char_length);
598
*to++= (uchar) length;
669
*to++= (unsigned char) length;
599
670
if (max_length > 255) // 2 byte length
600
*to++= (uchar) (length >> 8);
671
*to++= (unsigned char) (length >> 8);
601
672
memcpy(to, from, length);
602
673
ptr=save; // Restore org row pointer
603
674
return to+length;
625
696
Pointer into 'from' past the last byte copied from packed key.
629
Field_blob::unpack_key(uchar *to, const uchar *from, uint max_length,
699
const unsigned char *
700
Field_blob::unpack_key(unsigned char *to, const unsigned char *from, uint32_t max_length,
630
701
bool low_byte_first __attribute__((unused)))
632
703
/* get length of the blob key */
651
722
/** Create a packed key that will be used for storage from a MySQL key. */
654
Field_blob::pack_key_from_key_image(uchar *to, const uchar *from, uint max_length,
725
Field_blob::pack_key_from_key_image(unsigned char *to, const unsigned char *from, uint32_t max_length,
655
726
bool low_byte_first __attribute__((unused)))
657
uint length=uint2korr(from);
728
uint32_t length=uint2korr(from);
658
729
if (length > max_length)
659
730
length=max_length;
660
731
*to++= (char) (length & 255);
677
uint Field_blob::max_packed_col_length(uint max_length)
748
uint32_t Field_blob::max_packed_col_length(uint32_t max_length)
679
750
return (max_length > 255 ? 2 : 1)+max_length;
683
uint Field_blob::is_equal(Create_field *new_field)
754
uint32_t Field_blob::is_equal(Create_field *new_field)
685
756
if (compare_str_field_flags(new_field, flags))
791
bool Field_blob::in_read_set()
793
return bitmap_is_set(table->read_set, field_index);
797
bool Field_blob::in_write_set()
799
return bitmap_is_set(table->write_set, field_index);