1
/*****************************************************************************
3
Copyright (C) 1994, 2009, Innobase Oy. All Rights Reserved.
5
This program is free software; you can redistribute it and/or modify it under
6
the terms of the GNU General Public License as published by the Free Software
7
Foundation; version 2 of the License.
9
This program is distributed in the hope that it will be useful, but WITHOUT
10
ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
11
FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details.
13
You should have received a copy of the GNU General Public License along with
14
this program; if not, write to the Free Software Foundation, Inc., 51 Franklin
15
St, Fifth Floor, Boston, MA 02110-1301 USA
17
*****************************************************************************/
19
/********************************************************************//**
20
@file data/data0data.c
21
SQL data field and tuple
23
Created 5/30/1994 Heikki Tuuri
24
*************************************************************************/
26
#include "data0data.h"
29
#include "data0data.ic"
32
#ifndef UNIV_HOTBACKUP
35
#include "page0page.h"
37
#include "dict0dict.h"
41
#endif /* !UNIV_HOTBACKUP */
44
/** Dummy variable to catch access to uninitialized fields. In the
45
debug version, dtuple_create() will make all fields of dtuple_t point
47
UNIV_INTERN byte data_error;
49
# ifndef UNIV_DEBUG_VALGRIND
50
/** this is used to fool the compiler in dtuple_validate */
51
UNIV_INTERN ulint data_dummy;
52
# endif /* !UNIV_DEBUG_VALGRIND */
53
#endif /* UNIV_DEBUG */
55
#ifndef UNIV_HOTBACKUP
56
/*********************************************************************//**
57
Tests if dfield data length and content is equal to the given.
58
@return TRUE if equal */
61
dfield_data_is_binary_equal(
62
/*========================*/
63
const dfield_t* field, /*!< in: field */
64
ulint len, /*!< in: data length or UNIV_SQL_NULL */
65
const byte* data) /*!< in: data */
67
if (len != dfield_get_len(field)) {
72
if (len == UNIV_SQL_NULL) {
77
if (0 != memcmp(dfield_get_data(field), data, len)) {
85
/************************************************************//**
86
Compare two data tuples, respecting the collation of character fields.
87
@return 1, 0 , -1 if tuple1 is greater, equal, less, respectively,
93
const dtuple_t* tuple1, /*!< in: tuple 1 */
94
const dtuple_t* tuple2) /*!< in: tuple 2 */
99
ut_ad(tuple1 && tuple2);
100
ut_ad(tuple1->magic_n == DATA_TUPLE_MAGIC_N);
101
ut_ad(tuple2->magic_n == DATA_TUPLE_MAGIC_N);
102
ut_ad(dtuple_check_typed(tuple1));
103
ut_ad(dtuple_check_typed(tuple2));
105
n_fields = dtuple_get_n_fields(tuple1);
107
if (n_fields != dtuple_get_n_fields(tuple2)) {
109
return(n_fields < dtuple_get_n_fields(tuple2) ? -1 : 1);
112
for (i = 0; i < n_fields; i++) {
114
const dfield_t* field1 = dtuple_get_nth_field(tuple1, i);
115
const dfield_t* field2 = dtuple_get_nth_field(tuple2, i);
117
cmp = cmp_dfield_dfield(field1, field2);
127
/*********************************************************************//**
128
Sets number of fields used in a tuple. Normally this is set in
129
dtuple_create, but if you want later to set it smaller, you can use this. */
134
dtuple_t* tuple, /*!< in: tuple */
135
ulint n_fields) /*!< in: number of fields */
139
tuple->n_fields = n_fields;
140
tuple->n_fields_cmp = n_fields;
143
/**********************************************************//**
144
Checks that a data field is typed.
145
@return TRUE if ok */
148
dfield_check_typed_no_assert(
149
/*=========================*/
150
const dfield_t* field) /*!< in: data field */
152
if (dfield_get_type(field)->mtype > DATA_MYSQL
153
|| dfield_get_type(field)->mtype < DATA_VARCHAR) {
156
"InnoDB: Error: data field type %lu, len %lu\n",
157
(ulong) dfield_get_type(field)->mtype,
158
(ulong) dfield_get_len(field));
165
/**********************************************************//**
166
Checks that a data tuple is typed.
167
@return TRUE if ok */
170
dtuple_check_typed_no_assert(
171
/*=========================*/
172
const dtuple_t* tuple) /*!< in: tuple */
174
const dfield_t* field;
177
if (dtuple_get_n_fields(tuple) > REC_MAX_N_FIELDS) {
179
"InnoDB: Error: index entry has %lu fields\n",
180
(ulong) dtuple_get_n_fields(tuple));
182
fputs("InnoDB: Tuple contents: ", stderr);
183
dtuple_print(stderr, tuple);
189
for (i = 0; i < dtuple_get_n_fields(tuple); i++) {
191
field = dtuple_get_nth_field(tuple, i);
193
if (!dfield_check_typed_no_assert(field)) {
200
#endif /* !UNIV_HOTBACKUP */
203
/**********************************************************//**
204
Checks that a data field is typed. Asserts an error if not.
205
@return TRUE if ok */
210
const dfield_t* field) /*!< in: data field */
212
if (dfield_get_type(field)->mtype > DATA_MYSQL
213
|| dfield_get_type(field)->mtype < DATA_VARCHAR) {
216
"InnoDB: Error: data field type %lu, len %lu\n",
217
(ulong) dfield_get_type(field)->mtype,
218
(ulong) dfield_get_len(field));
226
/**********************************************************//**
227
Checks that a data tuple is typed. Asserts an error if not.
228
@return TRUE if ok */
233
const dtuple_t* tuple) /*!< in: tuple */
235
const dfield_t* field;
238
for (i = 0; i < dtuple_get_n_fields(tuple); i++) {
240
field = dtuple_get_nth_field(tuple, i);
242
ut_a(dfield_check_typed(field));
248
/**********************************************************//**
249
Validates the consistency of a tuple which must be complete, i.e,
250
all fields must have been set.
251
@return TRUE if ok */
256
const dtuple_t* tuple) /*!< in: tuple */
258
const dfield_t* field;
263
ut_ad(tuple->magic_n == DATA_TUPLE_MAGIC_N);
265
n_fields = dtuple_get_n_fields(tuple);
267
/* We dereference all the data of each field to test
270
for (i = 0; i < n_fields; i++) {
272
field = dtuple_get_nth_field(tuple, i);
273
len = dfield_get_len(field);
275
if (!dfield_is_null(field)) {
277
const byte* data = dfield_get_data(field);
278
#ifndef UNIV_DEBUG_VALGRIND
281
for (j = 0; j < len; j++) {
283
data_dummy += *data; /* fool the compiler not
288
#endif /* !UNIV_DEBUG_VALGRIND */
290
UNIV_MEM_ASSERT_RW(data, len);
294
ut_a(dtuple_check_typed(tuple));
298
#endif /* UNIV_DEBUG */
300
#ifndef UNIV_HOTBACKUP
301
/*************************************************************//**
302
Pretty prints a dfield value according to its data type. */
307
const dfield_t* dfield) /*!< in: dfield */
311
ulint len = dfield_get_len(dfield);
312
const byte *data = static_cast<const byte *>(dfield_get_data(dfield));
314
if (dfield_is_null(dfield)) {
315
fputs("NULL", stderr);
320
switch (dtype_get_mtype(dfield_get_type(dfield))) {
323
for (i = 0; i < len; i++) {
325
putc(isprint(c) ? c : ' ', stderr);
328
if (dfield_is_ext(dfield)) {
329
fputs("(external)", stderr);
333
ut_a(len == 4); /* only works for 32-bit integers */
334
fprintf(stderr, "%d", (int)mach_read_from_4(data));
341
/*************************************************************//**
342
Pretty prints a dfield value according to its data type. Also the hex string
343
is printed if a string contains non-printable characters. */
346
dfield_print_also_hex(
347
/*==================*/
348
const dfield_t* dfield) /*!< in: dfield */
354
ibool print_also_hex;
356
len = dfield_get_len(dfield);
357
data = static_cast<const byte *>(dfield_get_data(dfield));
359
if (dfield_is_null(dfield)) {
360
fputs("NULL", stderr);
365
prtype = dtype_get_prtype(dfield_get_type(dfield));
369
static const ulint UNSIGNED_MASK= 0x80000000;
371
switch (dtype_get_mtype(dfield_get_type(dfield))) {
375
val = mach_read_from_1(data);
377
if (!(prtype & DATA_UNSIGNED)) {
379
fprintf(stderr, "%ld", (long) val);
381
fprintf(stderr, "%lu", (ulong) val);
386
val = mach_read_from_2(data);
388
if (!(prtype & DATA_UNSIGNED)) {
390
fprintf(stderr, "%ld", (long) val);
392
fprintf(stderr, "%lu", (ulong) val);
397
val = mach_read_from_3(data);
399
if (!(prtype & DATA_UNSIGNED)) {
401
fprintf(stderr, "%ld", (long) val);
403
fprintf(stderr, "%lu", (ulong) val);
408
val = mach_read_from_4(data);
410
if (!(prtype & DATA_UNSIGNED)) {
411
val &= ~UNSIGNED_MASK;
412
fprintf(stderr, "%ld", (long) val);
414
fprintf(stderr, "%lu", (ulong) val);
419
id = mach_read_from_6(data);
420
fprintf(stderr, "%llu", (ullint) id);
424
id = mach_read_from_7(data);
425
fprintf(stderr, "%llu", (ullint) id);
428
id = mach_read_from_8(data);
429
fprintf(stderr, "%llu", (ullint) id);
437
switch (prtype & DATA_SYS_PRTYPE_MASK) {
439
id = mach_read_from_6(data);
441
fprintf(stderr, "trx_id " TRX_ID_FMT, id);
445
id = mach_read_from_7(data);
447
fprintf(stderr, "roll_ptr " TRX_ID_FMT, id);
451
id = mach_read_from_6(data);
453
fprintf(stderr, "row_id " TRX_ID_FMT, id);
457
id = mach_ull_read_compressed(data);
459
fprintf(stderr, "mix_id " TRX_ID_FMT, id);
465
print_also_hex = FALSE;
467
for (i = 0; i < len; i++) {
471
print_also_hex = TRUE;
473
fprintf(stderr, "\\x%02x", (unsigned char) c);
479
if (dfield_is_ext(dfield)) {
480
fputs("(external)", stderr);
483
if (!print_also_hex) {
487
data = static_cast<const byte *>(dfield_get_data(dfield));
493
fputs(" Hex: ",stderr);
495
for (i = 0; i < len; i++) {
496
fprintf(stderr, "%02lx", (ulint) *data++);
499
if (dfield_is_ext(dfield)) {
500
fputs("(external)", stderr);
505
/*************************************************************//**
506
Print a dfield value using ut_print_buf. */
511
FILE* f, /*!< in: output stream */
512
const dfield_t* dfield) /*!< in: dfield */
514
ulint len = dfield_get_len(dfield);
515
if (!dfield_is_null(dfield)) {
516
ulint print_len = ut_min(len, 1000);
517
ut_print_buf(f, dfield_get_data(dfield), print_len);
518
if (len != print_len) {
519
fprintf(f, "(total %lu bytes%s)",
521
dfield_is_ext(dfield) ? ", external" : "");
524
fputs(" SQL NULL", f);
528
/**********************************************************//**
529
The following function prints the contents of a tuple. */
534
FILE* f, /*!< in: output stream */
535
const dtuple_t* tuple) /*!< in: tuple */
540
n_fields = dtuple_get_n_fields(tuple);
542
fprintf(f, "DATA TUPLE: %lu fields;\n", (ulong) n_fields);
544
for (i = 0; i < n_fields; i++) {
545
fprintf(f, " %lu:", (ulong) i);
547
dfield_print_raw(f, dtuple_get_nth_field(tuple, i));
553
ut_ad(dtuple_validate(tuple));
556
/**************************************************************//**
557
Moves parts of long fields in entry to the big record vector so that
558
the size of tuple drops below the maximum record size allowed in the
559
database. Moves data only from those fields which are not necessary
560
to determine uniquely the insertion place of the tuple in the index.
561
@return own: created big record vector, NULL if we are not able to
562
shorten the entry enough, i.e., if there are too many fixed-length or
563
short fields in entry or the index is clustered */
566
dtuple_convert_big_rec(
567
/*===================*/
568
dict_index_t* index, /*!< in: index */
569
dtuple_t* entry, /*!< in/out: index entry */
570
ulint* n_ext) /*!< in/out: number of
571
externally stored columns */
576
dict_field_t* ifield;
580
ulint local_prefix_len;
582
if (UNIV_UNLIKELY(!dict_index_is_clust(index))) {
586
if (dict_table_get_format(index->table) < DICT_TF_FORMAT_ZIP) {
587
/* up to MySQL 5.1: store a 768-byte prefix locally */
588
local_len = BTR_EXTERN_FIELD_REF_SIZE + DICT_MAX_INDEX_COL_LEN;
590
/* new-format table: do not store any BLOB prefix locally */
591
local_len = BTR_EXTERN_FIELD_REF_SIZE;
594
ut_a(dtuple_check_typed_no_assert(entry));
596
size = rec_get_converted_size(index, entry, *n_ext);
598
if (UNIV_UNLIKELY(size > 1000000000)) {
600
"InnoDB: Warning: tuple size very big: %lu\n",
602
fputs("InnoDB: Tuple contents: ", stderr);
603
dtuple_print(stderr, entry);
607
heap = mem_heap_create(size + dtuple_get_n_fields(entry)
608
* sizeof(big_rec_field_t) + 1000);
610
vector = static_cast<big_rec_t *>(mem_heap_alloc(heap, sizeof(big_rec_t)));
613
vector->fields = static_cast<big_rec_field_t *>(mem_heap_alloc(heap, dtuple_get_n_fields(entry)
614
* sizeof(big_rec_field_t)));
616
/* Decide which fields to shorten: the algorithm is to look for
617
a variable-length field that yields the biggest savings when
622
while (page_zip_rec_needs_ext(rec_get_converted_size(index, entry,
624
dict_table_is_comp(index->table),
625
dict_index_get_n_fields(index),
626
dict_table_zip_size(index->table))) {
629
ulint longest_i = ULINT_MAX;
633
for (i = dict_index_get_n_unique_in_tree(index);
634
i < dtuple_get_n_fields(entry); i++) {
637
dfield = dtuple_get_nth_field(entry, i);
638
ifield = dict_index_get_nth_field(index, i);
640
/* Skip fixed-length, NULL, externally stored,
643
if (ifield->fixed_len
644
|| dfield_is_null(dfield)
645
|| dfield_is_ext(dfield)
646
|| dfield_get_len(dfield) <= local_len
647
|| dfield_get_len(dfield)
648
<= BTR_EXTERN_FIELD_REF_SIZE * 2) {
652
savings = dfield_get_len(dfield) - local_len;
654
/* Check that there would be savings */
655
if (longest >= savings) {
659
/* In DYNAMIC and COMPRESSED format, store
660
locally any non-BLOB columns whose maximum
661
length does not exceed 256 bytes. This is
662
because there is no room for the "external
663
storage" flag when the maximum length is 255
664
bytes or less. This restriction trivially
665
holds in REDUNDANT and COMPACT format, because
666
there we always store locally columns whose
667
length is up to local_len == 788 bytes.
668
@see rec_init_offsets_comp_ordinary */
669
if (ifield->col->mtype != DATA_BLOB
670
&& ifield->col->len < 256) {
674
/* In DYNAMIC and COMPRESSED format, store
675
locally any non-BLOB columns whose maximum
676
length does not exceed 256 bytes. This is
677
because there is no room for the "external
678
storage" flag when the maximum length is 255
679
bytes or less. This restriction trivially
680
holds in REDUNDANT and COMPACT format, because
681
there we always store locally columns whose
682
length is up to local_len == 788 bytes.
683
@see rec_init_offsets_comp_ordinary */
684
if (ifield->col->mtype != DATA_BLOB
685
&& ifield->col->len < 256) {
689
/* In DYNAMIC and COMPRESSED format, store
690
locally any non-BLOB columns whose maximum
691
length does not exceed 256 bytes. This is
692
because there is no room for the "external
693
storage" flag when the maximum length is 255
694
bytes or less. This restriction trivially
695
holds in REDUNDANT and COMPACT format, because
696
there we always store locally columns whose
697
length is up to local_len == 788 bytes.
698
@see rec_init_offsets_comp_ordinary */
699
if (ifield->col->mtype != DATA_BLOB
700
&& ifield->col->len < 256) {
712
/* Cannot shorten more */
719
/* Move data from field longest_i to big rec vector.
721
We store the first bytes locally to the record. Then
722
we can calculate all ordering fields in all indexes
723
from locally stored data. */
725
dfield = dtuple_get_nth_field(entry, longest_i);
726
ifield = dict_index_get_nth_field(index, longest_i);
727
local_prefix_len = local_len - BTR_EXTERN_FIELD_REF_SIZE;
729
b = &vector->fields[n_fields];
730
b->field_no = longest_i;
731
b->len = dfield_get_len(dfield) - local_prefix_len;
732
b->data = (char*) dfield_get_data(dfield) + local_prefix_len;
734
/* Allocate the locally stored part of the column. */
735
data = static_cast<unsigned char *>(mem_heap_alloc(heap, local_len));
737
/* Copy the local prefix. */
738
memcpy(data, dfield_get_data(dfield), local_prefix_len);
739
/* Clear the extern field reference (BLOB pointer). */
740
memset(data + local_prefix_len, 0, BTR_EXTERN_FIELD_REF_SIZE);
742
/* The following would fail the Valgrind checks in
743
page_cur_insert_rec_low() and page_cur_insert_rec_zip().
744
The BLOB pointers in the record will be initialized after
745
the record and the BLOBs have been written. */
746
UNIV_MEM_ALLOC(data + local_prefix_len,
747
BTR_EXTERN_FIELD_REF_SIZE);
750
dfield_set_data(dfield, data, local_len);
751
dfield_set_ext(dfield);
755
ut_ad(n_fields < dtuple_get_n_fields(entry));
758
vector->n_fields = n_fields;
762
/**************************************************************//**
763
Puts back to entry the data stored in vector. Note that to ensure the
764
fields in entry can accommodate the data, vector must have been created
765
from entry with dtuple_convert_big_rec. */
768
dtuple_convert_back_big_rec(
769
/*========================*/
770
dict_index_t* /*index __attribute__((unused))*/, /*!< in: index */
771
dtuple_t* entry, /*!< in: entry whose data was put to vector */
772
big_rec_t* vector) /*!< in, own: big rec vector; it is
773
freed in this function */
775
big_rec_field_t* b = vector->fields;
776
const big_rec_field_t* const end = b + vector->n_fields;
778
for (; b < end; b++) {
782
dfield = dtuple_get_nth_field(entry, b->field_no);
783
local_len = dfield_get_len(dfield);
785
ut_ad(dfield_is_ext(dfield));
786
ut_ad(local_len >= BTR_EXTERN_FIELD_REF_SIZE);
788
local_len -= BTR_EXTERN_FIELD_REF_SIZE;
790
ut_ad(local_len <= DICT_MAX_INDEX_COL_LEN);
792
dfield_set_data(dfield,
793
(char*) b->data - local_len,
797
mem_heap_free(vector->heap);
799
#endif /* !UNIV_HOTBACKUP */