145 UNIV_INTERN ulint rec_dummy;
179 if (n == ULINT_UNDEFINED) {
183 nulls = rec - (REC_N_NEW_EXTRA_BYTES + 1);
193 field = dict_index_get_nth_field(index, i);
197 if (UNIV_UNLIKELY(!(byte) null_mask)) {
202 if (*nulls & null_mask) {
222 if (UNIV_UNLIKELY(col->
len > 255)
223 || UNIV_UNLIKELY(col->
mtype == DATA_BLOB)) {
259 const byte* nulls = rec - (extra + 1);
260 const byte* lens = nulls
269 offsets[2] = (ulint) rec;
270 offsets[3] = (ulint) index;
277 field = dict_index_get_nth_field(index, i);
282 if (UNIV_UNLIKELY(!(byte) null_mask)) {
287 if (*nulls & null_mask) {
293 len = offs | REC_OFFS_SQL_NULL;
311 if (UNIV_UNLIKELY(col->
len > 255)
312 || UNIV_UNLIKELY(col->
mtype
319 offs += len & 0x3fff;
320 if (UNIV_UNLIKELY(len
324 any_ext = REC_OFFS_EXTERNAL;
340 rec_offs_base(offsets)[i + 1] = len;
343 *rec_offs_base(offsets)
344 = (rec - (lens + 1)) | REC_OFFS_COMPACT | any_ext;
373 rec_offs_make_valid(rec, index, offsets);
381 ulint n_node_ptr_field = ULINT_UNDEFINED;
383 switch (UNIV_EXPECT(status, REC_STATUS_ORDINARY)) {
384 case REC_STATUS_INFIMUM:
385 case REC_STATUS_SUPREMUM:
387 rec_offs_base(offsets)[0]
388 = REC_N_NEW_EXTRA_BYTES | REC_OFFS_COMPACT;
389 rec_offs_base(offsets)[1] = 8;
391 case REC_STATUS_NODE_PTR:
395 case REC_STATUS_ORDINARY:
397 REC_N_NEW_EXTRA_BYTES,
402 nulls = rec - (REC_N_NEW_EXTRA_BYTES + 1);
410 if (UNIV_UNLIKELY(i == n_node_ptr_field)) {
415 field = dict_index_get_nth_field(index, i);
420 if (UNIV_UNLIKELY(!(byte) null_mask)) {
425 if (*nulls & null_mask) {
431 len = offs | REC_OFFS_SQL_NULL;
451 if (UNIV_UNLIKELY(col->
len > 255)
452 || UNIV_UNLIKELY(col->
mtype
464 ut_a(!(len & 0x4000));
465 offs += len & 0x3fff;
477 rec_offs_base(offsets)[i + 1] = len;
480 *rec_offs_base(offsets)
481 = (rec - (lens + 1)) | REC_OFFS_COMPACT;
484 offs = REC_N_OLD_EXTRA_BYTES;
487 *rec_offs_base(offsets) = offs;
490 offs = rec_1_get_field_end_info(rec, i);
491 if (offs & REC_1BYTE_SQL_NULL_MASK) {
492 offs &= ~REC_1BYTE_SQL_NULL_MASK;
493 offs |= REC_OFFS_SQL_NULL;
495 rec_offs_base(offsets)[1 + i] = offs;
499 *rec_offs_base(offsets) = offs;
502 offs = rec_2_get_field_end_info(rec, i);
503 if (offs & REC_2BYTE_SQL_NULL_MASK) {
504 offs &= ~REC_2BYTE_SQL_NULL_MASK;
505 offs |= REC_OFFS_SQL_NULL;
507 if (offs & REC_2BYTE_EXTERN_MASK) {
508 offs &= ~REC_2BYTE_EXTERN_MASK;
509 offs |= REC_OFFS_EXTERNAL;
510 *rec_offs_base(offsets) |= REC_OFFS_EXTERNAL;
512 rec_offs_base(offsets)[1 + i] = offs;
548 REC_STATUS_ORDINARY)) {
549 case REC_STATUS_ORDINARY:
552 case REC_STATUS_NODE_PTR:
555 case REC_STATUS_INFIMUM:
556 case REC_STATUS_SUPREMUM:
568 if (UNIV_UNLIKELY(n_fields < n)) {
572 size = n + (1 + REC_OFFS_HEADER_SIZE);
574 if (UNIV_UNLIKELY(!offsets)
576 if (UNIV_UNLIKELY(!*heap)) {
581 offsets =
static_cast<unsigned long *
>(
mem_heap_alloc(*heap, size *
sizeof(ulint)));
585 rec_offs_set_n_fields(offsets, n);
586 rec_init_offsets(rec, index, offsets);
615 ulint n_node_ptr_field;
622 if (UNIV_UNLIKELY(node_ptr)) {
624 n = n_node_ptr_field + 1;
626 n_node_ptr_field = ULINT_UNDEFINED;
631 rec_offs_set_n_fields(offsets, n);
642 if (UNIV_UNLIKELY(i == n_node_ptr_field)) {
647 field = dict_index_get_nth_field(index, i);
651 if (UNIV_UNLIKELY(!(byte) null_mask)) {
656 if (*nulls & null_mask) {
662 len = offs | REC_OFFS_SQL_NULL;
680 if (UNIV_UNLIKELY(col->
len > 255)
681 || UNIV_UNLIKELY(col->
mtype == DATA_BLOB)) {
687 offs += len & 0x3fff;
688 if (UNIV_UNLIKELY(len & 0x4000)) {
689 any_ext = REC_OFFS_EXTERNAL;
690 len = offs | REC_OFFS_EXTERNAL;
704 rec_offs_base(offsets)[i + 1] = len;
707 ut_ad(lens >= extra);
708 *rec_offs_base(offsets) = (lens - extra + REC_N_NEW_EXTRA_BYTES)
709 | REC_OFFS_COMPACT | any_ext;
733 os = rec_1_get_field_start_offs(rec, n);
735 next_os = rec_1_get_field_end_info(rec, n);
737 if (next_os & REC_1BYTE_SQL_NULL_MASK) {
738 *len = UNIV_SQL_NULL;
743 next_os = next_os & ~REC_1BYTE_SQL_NULL_MASK;
745 os = rec_2_get_field_start_offs(rec, n);
747 next_os = rec_2_get_field_end_info(rec, n);
749 if (next_os & REC_2BYTE_SQL_NULL_MASK) {
750 *len = UNIV_SQL_NULL;
755 next_os = next_os & ~(REC_2BYTE_SQL_NULL_MASK
756 | REC_2BYTE_EXTERN_MASK);
761 ut_ad(*len < UNIV_PAGE_SIZE);
789 extra_size = REC_N_NEW_EXTRA_BYTES
794 for (i = 0; i < n_fields; i++) {
799 field = dict_index_get_nth_field(index, i);
803 ut_ad(dict_col_type_assert_equal(col,
804 dfield_get_type(&fields[i])));
812 ut_ad(len <= col->len || col->
mtype == DATA_BLOB);
830 || (col->
len < 256 && col->
mtype != DATA_BLOB)) {
842 if (UNIV_LIKELY_NULL(extra)) {
846 return(extra_size + data_size);
870 switch (UNIV_EXPECT(status, REC_STATUS_ORDINARY)) {
871 case REC_STATUS_ORDINARY:
875 case REC_STATUS_NODE_PTR:
879 size = REC_NODE_PTR_SIZE;
881 case REC_STATUS_INFIMUM:
882 case REC_STATUS_SUPREMUM:
884 if (UNIV_LIKELY_NULL(extra)) {
885 *extra = REC_N_NEW_EXTRA_BYTES;
887 return(REC_N_NEW_EXTRA_BYTES + 8);
890 return(ULINT_UNDEFINED);
901 rec_set_nth_field_null_bit(
911 info = rec_1_get_field_end_info(rec, i);
914 info = info | REC_1BYTE_SQL_NULL_MASK;
916 info = info & ~REC_1BYTE_SQL_NULL_MASK;
919 rec_1_set_field_end_info(rec, i, info);
924 info = rec_2_get_field_end_info(rec, i);
927 info = info | REC_2BYTE_SQL_NULL_MASK;
929 info = info & ~REC_2BYTE_SQL_NULL_MASK;
932 rec_2_set_field_end_info(rec, i, info);
940 rec_set_nth_field_sql_null(
947 offset = rec_get_field_start_offs(rec, n);
951 rec_set_nth_field_null_bit(rec, n, TRUE);
960 rec_convert_dtuple_to_rec_old(
975 ut_ad(buf && dtuple);
976 ut_ad(dtuple_validate(dtuple));
990 memset(buf, 0xff, rec - buf + data_size);
993 rec_set_n_fields_old(rec, n_fields);
997 & REC_INFO_BITS_MASK);
1003 if (!n_ext && data_size <= REC_1BYTE_OFFS_LIMIT) {
1005 rec_set_1byte_offs_flag(rec, TRUE);
1007 for (i = 0; i < n_fields; i++) {
1009 field = dtuple_get_nth_field(dtuple, i);
1013 dfield_get_type(field), 0);
1017 ored_offset = end_offset
1018 | REC_1BYTE_SQL_NULL_MASK;
1023 memcpy(rec + end_offset,
1024 dfield_get_data(field), len);
1027 ored_offset = end_offset;
1030 rec_1_set_field_end_info(rec, i, ored_offset);
1033 rec_set_1byte_offs_flag(rec, FALSE);
1035 for (i = 0; i < n_fields; i++) {
1037 field = dtuple_get_nth_field(dtuple, i);
1041 dfield_get_type(field), 0);
1045 ored_offset = end_offset
1046 | REC_2BYTE_SQL_NULL_MASK;
1051 memcpy(rec + end_offset,
1052 dfield_get_data(field), len);
1055 ored_offset = end_offset;
1058 ored_offset |= REC_2BYTE_EXTERN_MASK;
1062 rec_2_set_field_end_info(rec, i, ored_offset);
1092 ulint n_node_ptr_field;
1094 ulint null_mask = 1;
1096 ut_ad(extra == 0 || extra == REC_N_NEW_EXTRA_BYTES);
1097 ut_ad(n_fields > 0);
1099 switch (UNIV_EXPECT(status, REC_STATUS_ORDINARY)) {
1100 case REC_STATUS_ORDINARY:
1102 n_node_ptr_field = ULINT_UNDEFINED;
1104 case REC_STATUS_NODE_PTR:
1106 n_node_ptr_field = n_fields - 1;
1108 case REC_STATUS_INFIMUM:
1109 case REC_STATUS_SUPREMUM:
1110 ut_ad(n_fields == 1);
1111 n_node_ptr_field = ULINT_UNDEFINED;
1119 nulls = rec - (extra + 1);
1122 memset(lens + 1, 0, nulls - lens);
1126 for (i = 0, field = fields; i < n_fields; i++, field++) {
1129 type = dfield_get_type(field);
1132 if (UNIV_UNLIKELY(i == n_node_ptr_field)) {
1135 memcpy(end, dfield_get_data(field), len);
1144 if (UNIV_UNLIKELY(!(byte) null_mask)) {
1149 ut_ad(*nulls < null_mask);
1153 *nulls |= null_mask;
1163 ifield = dict_index_get_nth_field(index, i);
1172 ut_ad(len == fixed_len);
1176 || ifield->
col->
mtype == DATA_BLOB);
1177 ut_ad(len <= REC_MAX_INDEX_COL_LEN
1179 *lens-- = (byte) (len >> 8) | 0xc0;
1180 *lens-- = (byte) len;
1188 *lens-- = (byte) len;
1191 *lens-- = (byte) (len >> 8) | 0x80;
1192 *lens-- = (byte) len;
1196 memcpy(end, dfield_get_data(field), len);
1207 rec_convert_dtuple_to_rec_new(
1222 rec = buf + extra_size;
1225 rec, REC_N_NEW_EXTRA_BYTES, index, status,
1251 ut_ad(buf && index && dtuple);
1252 ut_ad(dtuple_validate(dtuple));
1256 rec = rec_convert_dtuple_to_rec_new(buf, index, dtuple);
1258 rec = rec_convert_dtuple_to_rec_old(buf, dtuple, n_ext);
1264 ulint offsets_[REC_OFFS_NORMAL_SIZE];
1265 const ulint* offsets;
1267 rec_offs_init(offsets_);
1269 offsets = rec_get_offsets(rec, index,
1270 offsets_, ULINT_UNDEFINED, &heap);
1280 if (UNIV_LIKELY_NULL(heap)) {
1303 ulint offsets_[REC_OFFS_NORMAL_SIZE];
1304 ulint* offsets = offsets_;
1305 rec_offs_init(offsets_);
1307 offsets = rec_get_offsets(rec, index, offsets, n_fields, &heap);
1315 for (i = 0; i < n_fields; i++) {
1320 field = dtuple_get_nth_field(tuple, i);
1321 data = rec_get_nth_field(rec, offsets, i, &len);
1323 if (len != UNIV_SQL_NULL) {
1339 rec_copy_prefix_to_buf_old(
1353 area_start = REC_N_OLD_EXTRA_BYTES + n_fields;
1355 area_start = REC_N_OLD_EXTRA_BYTES + 2 * n_fields;
1358 prefix_len = area_start + area_end;
1360 if ((*buf == NULL) || (*buf_size < prefix_len)) {
1365 *buf =
static_cast<byte *
>(mem_alloc2(prefix_len, buf_size));
1368 ut_memcpy(*buf, rec - area_start, prefix_len);
1370 copy_rec = *buf + area_start;
1372 rec_set_n_fields_old(copy_rec, n_fields);
1401 UNIV_PREFETCH_RW(*buf);
1404 ut_ad(rec_validate_old(rec));
1405 return(rec_copy_prefix_to_buf_old(
1407 rec_get_field_start_offs(rec, n_fields),
1414 case REC_STATUS_ORDINARY:
1417 case REC_STATUS_NODE_PTR:
1421 case REC_STATUS_INFIMUM:
1422 case REC_STATUS_SUPREMUM:
1429 nulls = rec - (REC_N_NEW_EXTRA_BYTES + 1);
1431 UNIV_PREFETCH_R(lens);
1436 for (i = 0; i < n_fields; i++) {
1440 field = dict_index_get_nth_field(index, i);
1443 if (!(col->
prtype & DATA_NOT_NULL)) {
1445 if (UNIV_UNLIKELY(!(byte) null_mask)) {
1450 if (*nulls & null_mask) {
1461 ulint len = *lens--;
1469 if (col->
len > 255 || col->
mtype == DATA_BLOB) {
1475 UNIV_PREFETCH_R(lens);
1482 UNIV_PREFETCH_R(rec + prefix_len);
1484 prefix_len += rec - (lens + 1);
1486 if ((*buf == NULL) || (*buf_size < prefix_len)) {
1491 *buf =
static_cast<byte *
>(mem_alloc2(prefix_len, buf_size));
1494 memcpy(*buf, lens + 1, prefix_len);
1496 return(*buf + (rec - (lens + 1)));
1518 if ((n_fields == 0) || (n_fields > REC_MAX_N_FIELDS)) {
1519 fprintf(stderr,
"InnoDB: Error: record has %lu fields\n",
1524 for (i = 0; i < n_fields; i++) {
1525 data = rec_get_nth_field_old(rec, i, &len);
1527 if (!((len < UNIV_PAGE_SIZE) || (len == UNIV_SQL_NULL))) {
1529 "InnoDB: Error: record field %lu len %lu\n",
1535 if (len != UNIV_SQL_NULL) {
1537 sum += *(data + len -1);
1548 "InnoDB: Error: record len should be %lu, len %lu\n",
1567 const ulint* offsets)
1579 if ((n_fields == 0) || (n_fields > REC_MAX_N_FIELDS)) {
1580 fprintf(stderr,
"InnoDB: Error: record has %lu fields\n",
1587 for (i = 0; i < n_fields; i++) {
1588 data = rec_get_nth_field(rec, offsets, i, &len);
1590 if (!((len < UNIV_PAGE_SIZE) || (len == UNIV_SQL_NULL))) {
1592 "InnoDB: Error: record field %lu len %lu\n",
1598 if (len != UNIV_SQL_NULL) {
1600 sum += *(data + len -1);
1611 "InnoDB: Error: record len should be %lu, len %lu\n",
1620 ut_a(rec_validate_old(rec));
1644 fprintf(file,
"PHYSICAL RECORD: n_fields %lu;"
1645 " %u-byte offsets; info bits %lu\n",
1650 for (i = 0; i < n; i++) {
1652 data = rec_get_nth_field_old(rec, i, &len);
1654 fprintf(file,
" %lu:", (ulong) i);
1656 if (len != UNIV_SQL_NULL) {
1663 fprintf(file,
" (total %lu bytes)",
1667 fprintf(file,
" SQL NULL, size %lu ",
1675 rec_validate_old(rec);
1678 #ifndef UNIV_HOTBACKUP
1688 const ulint* offsets)
1696 data = rec_get_nth_field(rec, offsets, i, &len);
1698 fprintf(file,
" %lu:", (ulong) i);
1700 if (len != UNIV_SQL_NULL) {
1707 fprintf(file,
" (total %lu bytes)",
1711 fputs(
" SQL NULL", file);
1726 const ulint* offsets)
1737 fprintf(file,
"PHYSICAL RECORD: n_fields %lu;"
1738 " compact format; info bits %lu\n",
1763 ulint offsets_[REC_OFFS_NORMAL_SIZE];
1764 rec_offs_init(offsets_);
1767 rec_get_offsets(rec, index, offsets_,
1768 ULINT_UNDEFINED, &heap));
1769 if (UNIV_LIKELY_NULL(heap)) {
UNIV_INLINE ulint rec_get_converted_extra_size(ulint data_size, ulint n_fields, ulint n_ext) __attribute__((const ))
UNIV_INLINE ibool rec_get_1byte_offs_flag(const rec_t *rec)
UNIV_INTERN rec_t * rec_copy_prefix_to_buf(const rec_t *rec, const dict_index_t *index, ulint n_fields, byte **buf, ulint *buf_size)
UNIV_INTERN void rec_copy_prefix_to_dtuple(dtuple_t *tuple, const rec_t *rec, const dict_index_t *index, ulint n_fields, mem_heap_t *heap)
UNIV_INTERN void rec_print_comp(FILE *file, const rec_t *rec, const ulint *offsets)
UNIV_INLINE ulint dict_index_get_n_fields(const dict_index_t *index)
UNIV_INTERN ulint rec_get_nth_field_offs_old(const rec_t *rec, ulint n, ulint *len)
UNIV_INLINE ulint rec_get_nth_field_size(const rec_t *rec, ulint n)
UNIV_INLINE ulint rec_get_n_fields_old(const rec_t *rec)
UNIV_INLINE ulint dfield_is_ext(const dfield_t *field)
UNIV_INLINE ulint rec_offs_data_size(const ulint *offsets)
UNIV_INLINE void * ut_memcpy(void *dest, const void *sour, ulint n)
UNIV_INTERN void ut_print_buf(FILE *file, const void *buf, ulint len)
UNIV_INTERN void * mem_heap_dup(mem_heap_t *heap, const void *data, ulint len)
UNIV_INTERN void rec_init_offsets_comp_ordinary(const rec_t *rec, ulint extra, const dict_index_t *index, ulint *offsets)
UNIV_INLINE ibool dict_table_is_comp(const dict_table_t *table)
UNIV_INLINE ulint rec_offs_nth_extern(const ulint *offsets, ulint n)
UNIV_INLINE ulint dtype_get_mtype(const dtype_t *type)
UNIV_INTERN void rec_print_new(FILE *file, const rec_t *rec, const ulint *offsets)
UNIV_INTERN ulint rec_get_converted_size_comp_prefix(const dict_index_t *index, const dfield_t *fields, ulint n_fields, ulint *extra)
UNIV_INTERN void rec_print(FILE *file, const rec_t *rec, const dict_index_t *index)
#define mem_heap_free(heap)
UNIV_INTERN rec_t * rec_convert_dtuple_to_rec(byte *buf, const dict_index_t *index, const dtuple_t *dtuple, ulint n_ext)
UNIV_INLINE ulint dtype_get_sql_null_size(const dtype_t *type, ulint comp)
UNIV_INTERN ulint * rec_get_offsets_func(const rec_t *rec, const dict_index_t *index, ulint *offsets, ulint n_fields, mem_heap_t **heap, const char *file, ulint line)
UNIV_INLINE ulint dtuple_get_n_fields(const dtuple_t *tuple)
UNIV_INLINE ulint rec_get_data_size_old(const rec_t *rec)
UNIV_INLINE ulint dict_index_get_n_unique_in_tree(const dict_index_t *index)
UNIV_INLINE void dfield_set_data(dfield_t *field, const void *data, ulint len)
UNIV_INLINE ulint dfield_get_len(const dfield_t *field)
UNIV_INLINE ulint dtype_get_len(const dtype_t *type)
UNIV_INLINE ulint rec_offs_comp(const ulint *offsets)
UNIV_INLINE ulint rec_get_status(const rec_t *rec)
UNIV_INLINE void rec_set_info_bits_old(rec_t *rec, ulint bits)
UNIV_INLINE ulint dict_index_is_clust(const dict_index_t *index) __attribute__((pure))
UNIV_INTERN ulint rec_get_converted_size_comp(const dict_index_t *index, ulint status, const dfield_t *fields, ulint n_fields, ulint *extra)
UNIV_INTERN ibool dtuple_check_typed(const dtuple_t *tuple)
UNIV_INTERN void rec_get_offsets_reverse(const byte *extra, const dict_index_t *index, ulint node_ptr, ulint *offsets)
UNIV_INLINE void dtuple_set_info_bits(dtuple_t *tuple, ulint info_bits)
UNIV_INLINE const dict_col_t * dict_field_get_col(const dict_field_t *field)
UNIV_INLINE void * mem_heap_alloc(mem_heap_t *heap, ulint n)
UNIV_INLINE ulint dtuple_get_info_bits(const dtuple_t *tuple)
UNIV_INLINE mem_heap_t * mem_heap_create_func(ulint n, ulint type, const char *file_name, ulint line)
UNIV_INLINE ulint rec_offs_n_fields(const ulint *offsets)
UNIV_INLINE ulint dfield_is_null(const dfield_t *field)
UNIV_INLINE ulint dtuple_get_data_size(const dtuple_t *tuple, ulint comp)
#define BTR_EXTERN_FIELD_REF_SIZE
UNIV_INTERN ibool rec_validate(const rec_t *rec, const ulint *offsets)
UNIV_INLINE void dfield_set_null(dfield_t *field)
UNIV_INTERN void rec_convert_dtuple_to_rec_comp(rec_t *rec, ulint extra, const dict_index_t *index, ulint status, const dfield_t *fields, ulint n_fields)
UNIV_INLINE void data_write_sql_null(byte *data, ulint len)
UNIV_INLINE void rec_set_info_and_status_bits(rec_t *rec, ulint bits)
UNIV_INTERN void rec_print_old(FILE *file, const rec_t *rec)
UNIV_INLINE ulint rec_get_info_bits(const rec_t *rec, ulint comp)
UNIV_INLINE ulint rec_offs_get_n_alloc(const ulint *offsets)
#define UT_BITS_IN_BYTES(b)
UNIV_INLINE void rec_offs_set_n_alloc(ulint *offsets, ulint n_alloc)
UNIV_INLINE ibool rec_offs_validate(const rec_t *rec, const dict_index_t *index, const ulint *offsets)
UNIV_INTERN ulint rec_get_n_extern_new(const rec_t *rec, dict_index_t *index, ulint n)
UNIV_INLINE ulint dtype_get_prtype(const dtype_t *type)