Skip to content
Projects
Groups
Snippets
Help
Loading...
Help
Support
Keyboard shortcuts
?
Submit feedback
Contribute to GitLab
Sign in / Register
Toggle navigation
M
MariaDB
Project overview
Project overview
Details
Activity
Releases
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Issues
0
Issues
0
List
Boards
Labels
Milestones
Merge Requests
0
Merge Requests
0
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Analytics
Analytics
CI / CD
Repository
Value Stream
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
nexedi
MariaDB
Commits
b3d6f517
Commit
b3d6f517
authored
Apr 25, 2005
by
marko@hundin.mysql.fi
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
InnoDB: Performance optimizations based on OProfile analysis
parent
ee7ed763
Changes
28
Hide whitespace changes
Inline
Side-by-side
Showing
28 changed files
with
929 additions
and
856 deletions
+929
-856
innobase/btr/btr0btr.c
innobase/btr/btr0btr.c
+71
-67
innobase/btr/btr0cur.c
innobase/btr/btr0cur.c
+91
-70
innobase/btr/btr0pcur.c
innobase/btr/btr0pcur.c
+30
-36
innobase/btr/btr0sea.c
innobase/btr/btr0sea.c
+54
-85
innobase/dict/dict0crea.c
innobase/dict/dict0crea.c
+1
-1
innobase/ibuf/ibuf0ibuf.c
innobase/ibuf/ibuf0ibuf.c
+22
-26
innobase/include/btr0btr.h
innobase/include/btr0btr.h
+3
-3
innobase/include/buf0buf.h
innobase/include/buf0buf.h
+2
-2
innobase/include/buf0buf.ic
innobase/include/buf0buf.ic
+2
-8
innobase/include/lock0lock.h
innobase/include/lock0lock.h
+1
-0
innobase/include/mach0data.h
innobase/include/mach0data.h
+21
-0
innobase/include/mach0data.ic
innobase/include/mach0data.ic
+31
-0
innobase/include/page0cur.h
innobase/include/page0cur.h
+4
-4
innobase/include/page0cur.ic
innobase/include/page0cur.ic
+6
-16
innobase/include/page0page.h
innobase/include/page0page.h
+42
-26
innobase/include/page0page.ic
innobase/include/page0page.ic
+143
-125
innobase/include/rem0rec.ic
innobase/include/rem0rec.ic
+3
-3
innobase/include/row0mysql.h
innobase/include/row0mysql.h
+1
-1
innobase/lock/lock0lock.c
innobase/lock/lock0lock.c
+86
-97
innobase/mtr/mtr0log.c
innobase/mtr/mtr0log.c
+6
-1
innobase/page/page0cur.c
innobase/page/page0cur.c
+25
-15
innobase/page/page0page.c
innobase/page/page0page.c
+72
-61
innobase/rem/rem0cmp.c
innobase/rem/rem0cmp.c
+1
-1
innobase/row/row0ins.c
innobase/row/row0ins.c
+20
-24
innobase/row/row0mysql.c
innobase/row/row0mysql.c
+1
-1
innobase/row/row0row.c
innobase/row/row0row.c
+2
-6
innobase/row/row0sel.c
innobase/row/row0sel.c
+181
-170
innobase/row/row0vers.c
innobase/row/row0vers.c
+7
-7
No files found.
innobase/btr/btr0btr.c
View file @
b3d6f517
...
@@ -138,13 +138,13 @@ btr_root_get(
...
@@ -138,13 +138,13 @@ btr_root_get(
ulint
space
;
ulint
space
;
ulint
root_page_no
;
ulint
root_page_no
;
page_t
*
root
;
page_t
*
root
;
ibool
comp
=
UT_LIST_GET_FIRST
(
tree
->
tree_indexes
)
->
table
->
comp
;
space
=
dict_tree_get_space
(
tree
);
space
=
dict_tree_get_space
(
tree
);
root_page_no
=
dict_tree_get_page
(
tree
);
root_page_no
=
dict_tree_get_page
(
tree
);
root
=
btr_page_get
(
space
,
root_page_no
,
RW_X_LATCH
,
mtr
);
root
=
btr_page_get
(
space
,
root_page_no
,
RW_X_LATCH
,
mtr
);
ut_a
(
page_is_comp
(
root
)
==
comp
);
ut_a
(
!!
page_is_comp
(
root
)
==
UT_LIST_GET_FIRST
(
tree
->
tree_indexes
)
->
table
->
comp
);
return
(
root
);
return
(
root
);
}
}
...
@@ -164,21 +164,19 @@ btr_get_prev_user_rec(
...
@@ -164,21 +164,19 @@ btr_get_prev_user_rec(
page_t
*
page
;
page_t
*
page
;
page_t
*
prev_page
;
page_t
*
prev_page
;
ulint
prev_page_no
;
ulint
prev_page_no
;
rec_t
*
prev_rec
;
ulint
space
;
ulint
space
;
page
=
buf_frame_align
(
rec
);
if
(
!
page_rec_is_infimum
(
rec
))
{
if
(
page_get_infimum_rec
(
page
)
!=
rec
)
{
prev_rec
=
page_rec_get_prev
(
rec
);
rec_t
*
prev_rec
=
page_rec_get_prev
(
rec
);
if
(
page_get_infimum_rec
(
page
)
!=
prev_rec
)
{
if
(
!
page_rec_is_infimum
(
prev_rec
)
)
{
return
(
prev_rec
);
return
(
prev_rec
);
}
}
}
}
page
=
buf_frame_align
(
rec
);
prev_page_no
=
btr_page_get_prev
(
page
,
mtr
);
prev_page_no
=
btr_page_get_prev
(
page
,
mtr
);
space
=
buf_frame_get_space_id
(
page
);
space
=
buf_frame_get_space_id
(
page
);
...
@@ -193,9 +191,7 @@ btr_get_prev_user_rec(
...
@@ -193,9 +191,7 @@ btr_get_prev_user_rec(
MTR_MEMO_PAGE_X_FIX
)));
MTR_MEMO_PAGE_X_FIX
)));
ut_a
(
page_is_comp
(
prev_page
)
==
page_is_comp
(
page
));
ut_a
(
page_is_comp
(
prev_page
)
==
page_is_comp
(
page
));
prev_rec
=
page_rec_get_prev
(
page_get_supremum_rec
(
prev_page
));
return
(
page_rec_get_prev
(
page_get_supremum_rec
(
prev_page
)));
return
(
prev_rec
);
}
}
return
(
NULL
);
return
(
NULL
);
...
@@ -216,21 +212,19 @@ btr_get_next_user_rec(
...
@@ -216,21 +212,19 @@ btr_get_next_user_rec(
page_t
*
page
;
page_t
*
page
;
page_t
*
next_page
;
page_t
*
next_page
;
ulint
next_page_no
;
ulint
next_page_no
;
rec_t
*
next_rec
;
ulint
space
;
ulint
space
;
page
=
buf_frame_align
(
rec
);
if
(
!
page_rec_is_supremum
(
rec
))
{
if
(
page_get_supremum_rec
(
page
)
!=
rec
)
{
next_rec
=
page_rec_get_next
(
rec
);
rec_t
*
next_rec
=
page_rec_get_next
(
rec
);
if
(
page_get_supremum_rec
(
page
)
!=
next_rec
)
{
if
(
!
page_rec_is_supremum
(
next_rec
)
)
{
return
(
next_rec
);
return
(
next_rec
);
}
}
}
}
page
=
buf_frame_align
(
rec
);
next_page_no
=
btr_page_get_next
(
page
,
mtr
);
next_page_no
=
btr_page_get_next
(
page
,
mtr
);
space
=
buf_frame_get_space_id
(
page
);
space
=
buf_frame_get_space_id
(
page
);
...
@@ -245,9 +239,7 @@ btr_get_next_user_rec(
...
@@ -245,9 +239,7 @@ btr_get_next_user_rec(
MTR_MEMO_PAGE_X_FIX
)));
MTR_MEMO_PAGE_X_FIX
)));
ut_a
(
page_is_comp
(
next_page
)
==
page_is_comp
(
page
));
ut_a
(
page_is_comp
(
next_page
)
==
page_is_comp
(
page
));
next_rec
=
page_rec_get_next
(
page_get_infimum_rec
(
next_page
));
return
(
page_rec_get_next
(
page_get_infimum_rec
(
next_page
)));
return
(
next_rec
);
}
}
return
(
NULL
);
return
(
NULL
);
...
@@ -574,8 +566,7 @@ btr_page_get_father_for_rec(
...
@@ -574,8 +566,7 @@ btr_page_get_father_for_rec(
ut_ad
(
mtr_memo_contains
(
mtr
,
dict_tree_get_lock
(
tree
),
ut_ad
(
mtr_memo_contains
(
mtr
,
dict_tree_get_lock
(
tree
),
MTR_MEMO_X_LOCK
));
MTR_MEMO_X_LOCK
));
ut_a
(
user_rec
!=
page_get_supremum_rec
(
page
));
ut_a
(
page_rec_is_user_rec
(
user_rec
));
ut_a
(
user_rec
!=
page_get_infimum_rec
(
page
));
ut_ad
(
dict_tree_get_page
(
tree
)
!=
buf_frame_get_page_no
(
page
));
ut_ad
(
dict_tree_get_page
(
tree
)
!=
buf_frame_get_page_no
(
page
));
...
@@ -599,6 +590,7 @@ btr_page_get_father_for_rec(
...
@@ -599,6 +590,7 @@ btr_page_get_father_for_rec(
if
(
btr_node_ptr_get_child_page_no
(
node_ptr
,
offsets
)
!=
if
(
btr_node_ptr_get_child_page_no
(
node_ptr
,
offsets
)
!=
buf_frame_get_page_no
(
page
))
{
buf_frame_get_page_no
(
page
))
{
rec_t
*
print_rec
;
fputs
(
"InnoDB: Dump of the child page:
\n
"
,
stderr
);
fputs
(
"InnoDB: Dump of the child page:
\n
"
,
stderr
);
buf_page_print
(
buf_frame_align
(
page
));
buf_page_print
(
buf_frame_align
(
page
));
fputs
(
"InnoDB: Dump of the parent page:
\n
"
,
stderr
);
fputs
(
"InnoDB: Dump of the parent page:
\n
"
,
stderr
);
...
@@ -613,11 +605,10 @@ btr_page_get_father_for_rec(
...
@@ -613,11 +605,10 @@ btr_page_get_father_for_rec(
(
ulong
)
(
ulong
)
btr_node_ptr_get_child_page_no
(
node_ptr
,
offsets
),
btr_node_ptr_get_child_page_no
(
node_ptr
,
offsets
),
(
ulong
)
buf_frame_get_page_no
(
page
));
(
ulong
)
buf_frame_get_page_no
(
page
));
offsets
=
rec_get_offsets
(
page_rec_get_next
(
print_rec
=
page_rec_get_next
(
page_get_infimum_rec
(
page
));
page_get_infimum_rec
(
page
))
,
index
,
offsets
=
rec_get_offsets
(
print_rec
,
index
,
offsets
,
ULINT_UNDEFINED
,
&
heap
);
offsets
,
ULINT_UNDEFINED
,
&
heap
);
page_rec_print
(
page_rec_get_next
(
page_get_infimum_rec
(
page
)),
page_rec_print
(
print_rec
,
offsets
);
offsets
);
offsets
=
rec_get_offsets
(
node_ptr
,
index
,
offsets
,
offsets
=
rec_get_offsets
(
node_ptr
,
index
,
offsets
,
ULINT_UNDEFINED
,
&
heap
);
ULINT_UNDEFINED
,
&
heap
);
page_rec_print
(
node_ptr
,
offsets
);
page_rec_print
(
node_ptr
,
offsets
);
...
@@ -664,7 +655,7 @@ btr_create(
...
@@ -664,7 +655,7 @@ btr_create(
ulint
type
,
/* in: type of the index */
ulint
type
,
/* in: type of the index */
ulint
space
,
/* in: space where created */
ulint
space
,
/* in: space where created */
dulint
index_id
,
/* in: index id */
dulint
index_id
,
/* in: index id */
ibool
comp
,
/* in: TRUE
=compact page format */
ulint
comp
,
/* in: nonzero
=compact page format */
mtr_t
*
mtr
)
/* in: mini-transaction handle */
mtr_t
*
mtr
)
/* in: mini-transaction handle */
{
{
ulint
page_no
;
ulint
page_no
;
...
@@ -855,11 +846,12 @@ btr_page_reorganize_low(
...
@@ -855,11 +846,12 @@ btr_page_reorganize_low(
ut_ad
(
mtr_memo_contains
(
mtr
,
buf_block_align
(
page
),
ut_ad
(
mtr_memo_contains
(
mtr
,
buf_block_align
(
page
),
MTR_MEMO_PAGE_X_FIX
));
MTR_MEMO_PAGE_X_FIX
));
ut_ad
(
!!
page_is_comp
(
page
)
==
index
->
table
->
comp
);
data_size1
=
page_get_data_size
(
page
);
data_size1
=
page_get_data_size
(
page
);
max_ins_size1
=
page_get_max_insert_size_after_reorganize
(
page
,
1
);
max_ins_size1
=
page_get_max_insert_size_after_reorganize
(
page
,
1
);
/* Write the log record */
/* Write the log record */
mlog_open_and_write_index
(
mtr
,
page
,
index
,
index
->
table
->
comp
mlog_open_and_write_index
(
mtr
,
page
,
index
,
page_is_comp
(
page
)
?
MLOG_COMP_PAGE_REORGANIZE
?
MLOG_COMP_PAGE_REORGANIZE
:
MLOG_PAGE_REORGANIZE
,
0
);
:
MLOG_PAGE_REORGANIZE
,
0
);
...
@@ -878,7 +870,7 @@ btr_page_reorganize_low(
...
@@ -878,7 +870,7 @@ btr_page_reorganize_low(
/* Recreate the page: note that global data on page (possible
/* Recreate the page: note that global data on page (possible
segment headers, next page-field, etc.) is preserved intact */
segment headers, next page-field, etc.) is preserved intact */
page_create
(
page
,
mtr
,
index
->
table
->
comp
);
page_create
(
page
,
mtr
,
page_is_comp
(
page
)
);
buf_block_align
(
page
)
->
check_index_page_at_flush
=
TRUE
;
buf_block_align
(
page
)
->
check_index_page_at_flush
=
TRUE
;
/* Copy the records from the temporary space to the recreated page;
/* Copy the records from the temporary space to the recreated page;
...
@@ -1071,7 +1063,7 @@ btr_root_raise_and_insert(
...
@@ -1071,7 +1063,7 @@ btr_root_raise_and_insert(
as there is no lower alphabetical limit to records in the leftmost
as there is no lower alphabetical limit to records in the leftmost
node of a level: */
node of a level: */
btr_set_min_rec_mark
(
node_ptr_rec
,
cursor
->
index
->
table
->
comp
,
mtr
);
btr_set_min_rec_mark
(
node_ptr_rec
,
page_is_comp
(
root
)
,
mtr
);
/* Free the memory heap */
/* Free the memory heap */
mem_heap_free
(
heap
);
mem_heap_free
(
heap
);
...
@@ -1152,7 +1144,6 @@ btr_page_get_split_rec_to_right(
...
@@ -1152,7 +1144,6 @@ btr_page_get_split_rec_to_right(
{
{
page_t
*
page
;
page_t
*
page
;
rec_t
*
insert_point
;
rec_t
*
insert_point
;
rec_t
*
supremum
;
page
=
btr_cur_get_page
(
cursor
);
page
=
btr_cur_get_page
(
cursor
);
insert_point
=
btr_cur_get_rec
(
cursor
);
insert_point
=
btr_cur_get_rec
(
cursor
);
...
@@ -1161,13 +1152,22 @@ btr_page_get_split_rec_to_right(
...
@@ -1161,13 +1152,22 @@ btr_page_get_split_rec_to_right(
the previous insert on the same page, we assume that there is a
the previous insert on the same page, we assume that there is a
pattern of sequential inserts here. */
pattern of sequential inserts here. */
if
(
page_header_get_ptr
(
page
,
PAGE_LAST_INSERT
)
==
insert_point
)
{
if
(
UNIV_LIKELY
(
page_header_get_ptr
(
page
,
PAGE_LAST_INSERT
)
==
insert_point
))
{
supremum
=
page_get_supremum_rec
(
page
);
rec_t
*
next_rec
;
if
(
page_rec_get_next
(
insert_point
)
!=
supremum
next_rec
=
page_rec_get_next
(
insert_point
);
&&
page_rec_get_next
(
page_rec_get_next
(
insert_point
))
!=
supremum
)
{
if
(
page_rec_is_supremum
(
next_rec
))
{
split_at_new:
/* Split at the new record to insert */
*
split_rec
=
NULL
;
}
else
{
rec_t
*
next_next_rec
=
page_rec_get_next
(
next_rec
);
if
(
page_rec_is_supremum
(
next_next_rec
))
{
goto
split_at_new
;
}
/* If there are >= 2 user records up from the insert
/* If there are >= 2 user records up from the insert
point, split all but 1 off. We want to keep one because
point, split all but 1 off. We want to keep one because
...
@@ -1176,12 +1176,8 @@ btr_page_get_split_rec_to_right(
...
@@ -1176,12 +1176,8 @@ btr_page_get_split_rec_to_right(
search position just by looking at the records on this
search position just by looking at the records on this
page. */
page. */
*
split_rec
=
page_rec_get_next
(
*
split_rec
=
next_next_rec
;
page_rec_get_next
(
insert_point
));
}
}
else
{
/* Else split at the new record to insert */
*
split_rec
=
NULL
;
}
return
(
TRUE
);
return
(
TRUE
);
}
}
...
@@ -1221,7 +1217,7 @@ btr_page_get_sure_split_rec(
...
@@ -1221,7 +1217,7 @@ btr_page_get_sure_split_rec(
page
=
btr_cur_get_page
(
cursor
);
page
=
btr_cur_get_page
(
cursor
);
insert_size
=
rec_get_converted_size
(
cursor
->
index
,
tuple
);
insert_size
=
rec_get_converted_size
(
cursor
->
index
,
tuple
);
free_space
=
page_get_free_space_of_empty
(
cursor
->
index
->
table
->
comp
);
free_space
=
page_get_free_space_of_empty
(
page_is_comp
(
page
)
);
/* free_space is now the free space of a created new page */
/* free_space is now the free space of a created new page */
...
@@ -1283,11 +1279,8 @@ btr_page_get_sure_split_rec(
...
@@ -1283,11 +1279,8 @@ btr_page_get_sure_split_rec(
}
else
{
}
else
{
next_rec
=
page_rec_get_next
(
rec
);
next_rec
=
page_rec_get_next
(
rec
);
}
}
if
(
next_rec
!=
page_get_supremum_rec
(
page
))
{
if
(
!
page_rec_is_supremum
(
next_rec
)))
{
if
(
UNIV_LIKELY_NULL
(
heap
))
{
rec
=
next_rec
;
mem_heap_free
(
heap
);
}
return
(
next_rec
);
}
}
}
}
...
@@ -1330,13 +1323,12 @@ btr_page_insert_fits(
...
@@ -1330,13 +1323,12 @@ btr_page_insert_fits(
ut_ad
(
!
split_rec
==
!
offsets
);
ut_ad
(
!
split_rec
==
!
offsets
);
ut_ad
(
!
offsets
ut_ad
(
!
offsets
||
cursor
->
index
->
table
->
comp
==
rec_offs_comp
(
offsets
));
||
page_is_comp
(
page
)
==
!!
rec_offs_comp
(
offsets
));
ut_ad
(
!
offsets
ut_ad
(
!
offsets
||
rec_offs_validate
(
split_rec
,
cursor
->
index
,
offsets
));
||
rec_offs_validate
(
split_rec
,
cursor
->
index
,
offsets
));
ut_ad
(
page_is_comp
(
page
)
==
cursor
->
index
->
table
->
comp
);
insert_size
=
rec_get_converted_size
(
cursor
->
index
,
tuple
);
insert_size
=
rec_get_converted_size
(
cursor
->
index
,
tuple
);
free_space
=
page_get_free_space_of_empty
(
cursor
->
index
->
table
->
comp
);
free_space
=
page_get_free_space_of_empty
(
page_is_comp
(
page
)
);
/* free_space is now the free space of a created new page */
/* free_space is now the free space of a created new page */
...
@@ -1833,14 +1825,15 @@ void
...
@@ -1833,14 +1825,15 @@ void
btr_set_min_rec_mark_log
(
btr_set_min_rec_mark_log
(
/*=====================*/
/*=====================*/
rec_t
*
rec
,
/* in: record */
rec_t
*
rec
,
/* in: record */
ibool
comp
,
/* TRUE
=compact record format */
ulint
comp
,
/* nonzero
=compact record format */
mtr_t
*
mtr
)
/* in: mtr */
mtr_t
*
mtr
)
/* in: mtr */
{
{
mlog_write_initial_log_record
(
rec
,
mlog_write_initial_log_record
(
rec
,
comp
?
MLOG_COMP_REC_MIN_MARK
:
MLOG_REC_MIN_MARK
,
mtr
);
comp
?
MLOG_COMP_REC_MIN_MARK
:
MLOG_REC_MIN_MARK
,
mtr
);
/* Write rec offset as a 2-byte ulint */
/* Write rec offset as a 2-byte ulint */
mlog_catenate_ulint
(
mtr
,
rec
-
buf_frame_align
(
rec
),
MLOG_2BYTES
);
mlog_catenate_ulint
(
mtr
,
ut_align_offset
(
rec
,
UNIV_PAGE_SIZE
),
MLOG_2BYTES
);
}
}
/********************************************************************
/********************************************************************
...
@@ -1853,7 +1846,7 @@ btr_parse_set_min_rec_mark(
...
@@ -1853,7 +1846,7 @@ btr_parse_set_min_rec_mark(
/* out: end of log record or NULL */
/* out: end of log record or NULL */
byte
*
ptr
,
/* in: buffer */
byte
*
ptr
,
/* in: buffer */
byte
*
end_ptr
,
/* in: buffer end */
byte
*
end_ptr
,
/* in: buffer end */
ibool
comp
,
/* in: TRUE
=compact page format */
ulint
comp
,
/* in: nonzero
=compact page format */
page_t
*
page
,
/* in: page or NULL */
page_t
*
page
,
/* in: page or NULL */
mtr_t
*
mtr
)
/* in: mtr or NULL */
mtr_t
*
mtr
)
/* in: mtr or NULL */
{
{
...
@@ -1865,6 +1858,8 @@ btr_parse_set_min_rec_mark(
...
@@ -1865,6 +1858,8 @@ btr_parse_set_min_rec_mark(
}
}
if
(
page
)
{
if
(
page
)
{
ut_a
(
!
page_is_comp
(
page
)
==
!
comp
);
rec
=
page
+
mach_read_from_2
(
ptr
);
rec
=
page
+
mach_read_from_2
(
ptr
);
btr_set_min_rec_mark
(
rec
,
comp
,
mtr
);
btr_set_min_rec_mark
(
rec
,
comp
,
mtr
);
...
@@ -1880,7 +1875,7 @@ void
...
@@ -1880,7 +1875,7 @@ void
btr_set_min_rec_mark
(
btr_set_min_rec_mark
(
/*=================*/
/*=================*/
rec_t
*
rec
,
/* in: record */
rec_t
*
rec
,
/* in: record */
ibool
comp
,
/* in: TRUE
=compact page format */
ulint
comp
,
/* in: nonzero
=compact page format */
mtr_t
*
mtr
)
/* in: mtr */
mtr_t
*
mtr
)
/* in: mtr */
{
{
ulint
info_bits
;
ulint
info_bits
;
...
@@ -2009,11 +2004,12 @@ btr_compress(
...
@@ -2009,11 +2004,12 @@ btr_compress(
ulint
max_ins_size
;
ulint
max_ins_size
;
ulint
max_ins_size_reorg
;
ulint
max_ins_size_reorg
;
ulint
level
;
ulint
level
;
ibool
comp
=
cursor
->
index
->
table
->
comp
;
ulint
comp
;
page
=
btr_cur_get_page
(
cursor
);
page
=
btr_cur_get_page
(
cursor
);
tree
=
btr_cur_get_tree
(
cursor
);
tree
=
btr_cur_get_tree
(
cursor
);
ut_a
(
comp
==
page_is_comp
(
page
));
comp
=
page_is_comp
(
page
);
ut_a
(
!!
comp
==
cursor
->
index
->
table
->
comp
);
ut_ad
(
mtr_memo_contains
(
mtr
,
dict_tree_get_lock
(
tree
),
ut_ad
(
mtr_memo_contains
(
mtr
,
dict_tree_get_lock
(
tree
),
MTR_MEMO_X_LOCK
));
MTR_MEMO_X_LOCK
));
...
@@ -2056,7 +2052,7 @@ btr_compress(
...
@@ -2056,7 +2052,7 @@ btr_compress(
n_recs
=
page_get_n_recs
(
page
);
n_recs
=
page_get_n_recs
(
page
);
data_size
=
page_get_data_size
(
page
);
data_size
=
page_get_data_size
(
page
);
ut_a
(
page_is_comp
(
merge_page
)
==
page_is_comp
(
page
)
);
ut_a
(
page_is_comp
(
merge_page
)
==
comp
);
max_ins_size_reorg
=
page_get_max_insert_size_after_reorganize
(
max_ins_size_reorg
=
page_get_max_insert_size_after_reorganize
(
merge_page
,
n_recs
);
merge_page
,
n_recs
);
...
@@ -2251,10 +2247,9 @@ btr_discard_page(
...
@@ -2251,10 +2247,9 @@ btr_discard_page(
node_ptr
=
page_rec_get_next
(
page_get_infimum_rec
(
merge_page
));
node_ptr
=
page_rec_get_next
(
page_get_infimum_rec
(
merge_page
));
ut_ad
(
node_ptr
!=
page_get_supremum_rec
(
merge_page
));
ut_ad
(
page_rec_is_user_rec
(
node_ptr
));
btr_set_min_rec_mark
(
node_ptr
,
btr_set_min_rec_mark
(
node_ptr
,
page_is_comp
(
merge_page
),
mtr
);
cursor
->
index
->
table
->
comp
,
mtr
);
}
}
btr_node_ptr_delete
(
tree
,
page
,
mtr
);
btr_node_ptr_delete
(
tree
,
page
,
mtr
);
...
@@ -2499,8 +2494,8 @@ btr_index_rec_validate(
...
@@ -2499,8 +2494,8 @@ btr_index_rec_validate(
*
offsets_
=
(
sizeof
offsets_
)
/
sizeof
*
offsets_
;
*
offsets_
=
(
sizeof
offsets_
)
/
sizeof
*
offsets_
;
page
=
buf_frame_align
(
rec
);
page
=
buf_frame_align
(
rec
);
if
(
index
->
type
&
DICT_UNIVERSAL
)
{
if
(
UNIV_UNLIKELY
(
index
->
type
&
DICT_UNIVERSAL
)
)
{
/* The insert buffer index tree can contain records from any
/* The insert buffer index tree can contain records from any
other index: we cannot check the number of fields or
other index: we cannot check the number of fields or
their length */
their length */
...
@@ -2508,9 +2503,18 @@ btr_index_rec_validate(
...
@@ -2508,9 +2503,18 @@ btr_index_rec_validate(
return
(
TRUE
);
return
(
TRUE
);
}
}
if
(
UNIV_UNLIKELY
(
!!
page_is_comp
(
page
)
!=
index
->
table
->
comp
))
{
btr_index_rec_validate_report
(
page
,
rec
,
index
);
fprintf
(
stderr
,
"InnoDB: compact flag=%lu, should be %lu
\n
"
,
(
ulong
)
!!
page_is_comp
(
page
),
(
ulong
)
index
->
table
->
comp
);
return
(
FALSE
);
}
n
=
dict_index_get_n_fields
(
index
);
n
=
dict_index_get_n_fields
(
index
);
if
(
!
index
->
table
->
comp
&&
rec_get_n_fields_old
(
rec
)
!=
n
)
{
if
(
!
page_is_comp
(
page
)
&&
UNIV_UNLIKELY
(
rec_get_n_fields_old
(
rec
)
!=
n
))
{
btr_index_rec_validate_report
(
page
,
rec
,
index
);
btr_index_rec_validate_report
(
page
,
rec
,
index
);
fprintf
(
stderr
,
"InnoDB: has %lu fields, should have %lu
\n
"
,
fprintf
(
stderr
,
"InnoDB: has %lu fields, should have %lu
\n
"
,
(
ulong
)
rec_get_n_fields_old
(
rec
),
(
ulong
)
n
);
(
ulong
)
rec_get_n_fields_old
(
rec
),
(
ulong
)
n
);
...
@@ -2774,7 +2778,7 @@ btr_validate_level(
...
@@ -2774,7 +2778,7 @@ btr_validate_level(
if
(
level
>
0
&&
left_page_no
==
FIL_NULL
)
{
if
(
level
>
0
&&
left_page_no
==
FIL_NULL
)
{
ut_a
(
REC_INFO_MIN_REC_FLAG
&
rec_get_info_bits
(
ut_a
(
REC_INFO_MIN_REC_FLAG
&
rec_get_info_bits
(
page_rec_get_next
(
page_get_infimum_rec
(
page
)),
page_rec_get_next
(
page_get_infimum_rec
(
page
)),
index
->
table
->
comp
));
page_is_comp
(
page
)
));
}
}
if
(
buf_frame_get_page_no
(
page
)
!=
dict_tree_get_page
(
tree
))
{
if
(
buf_frame_get_page_no
(
page
)
!=
dict_tree_get_page
(
tree
))
{
...
@@ -2930,7 +2934,7 @@ btr_validate_level(
...
@@ -2930,7 +2934,7 @@ btr_validate_level(
mtr_commit
(
&
mtr
);
mtr_commit
(
&
mtr
);
if
(
right_page_no
!=
FIL_NULL
)
{
if
(
right_page_no
!=
FIL_NULL
)
{
ibool
comp
=
page_is_comp
(
page
);
ulint
comp
=
page_is_comp
(
page
);
mtr_start
(
&
mtr
);
mtr_start
(
&
mtr
);
page
=
btr_page_get
(
space
,
right_page_no
,
RW_X_LATCH
,
&
mtr
);
page
=
btr_page_get
(
space
,
right_page_no
,
RW_X_LATCH
,
&
mtr
);
...
...
innobase/btr/btr0cur.c
View file @
b3d6f517
...
@@ -505,8 +505,9 @@ btr_cur_search_to_nth_level(
...
@@ -505,8 +505,9 @@ btr_cur_search_to_nth_level(
if
(
level
>
0
)
{
if
(
level
>
0
)
{
/* x-latch the page */
/* x-latch the page */
ut_a
(
page_is_comp
(
btr_page_get
(
space
,
page
=
btr_page_get
(
space
,
page_no
,
RW_X_LATCH
,
mtr
))
page_no
,
RW_X_LATCH
,
mtr
);
ut_a
(
!!
page_is_comp
(
page
)
==
index
->
table
->
comp
);
==
index
->
table
->
comp
);
}
}
...
@@ -961,7 +962,7 @@ btr_cur_optimistic_insert(
...
@@ -961,7 +962,7 @@ btr_cur_optimistic_insert(
rec_size
=
rec_get_converted_size
(
index
,
entry
);
rec_size
=
rec_get_converted_size
(
index
,
entry
);
if
(
rec_size
>=
if
(
rec_size
>=
ut_min
(
page_get_free_space_of_empty
(
index
->
table
->
comp
)
/
2
,
ut_min
(
page_get_free_space_of_empty
(
page_is_comp
(
page
)
)
/
2
,
REC_MAX_DATA_SIZE
))
{
REC_MAX_DATA_SIZE
))
{
/* The record is so big that we have to store some fields
/* The record is so big that we have to store some fields
...
@@ -1027,7 +1028,7 @@ btr_cur_optimistic_insert(
...
@@ -1027,7 +1028,7 @@ btr_cur_optimistic_insert(
*
rec
=
page_cur_insert_rec_low
(
page_cursor
,
entry
,
index
,
*
rec
=
page_cur_insert_rec_low
(
page_cursor
,
entry
,
index
,
NULL
,
NULL
,
mtr
);
NULL
,
NULL
,
mtr
);
if
(
!
(
*
rec
))
{
if
(
UNIV_UNLIKELY
(
!
(
*
rec
)
))
{
/* If the record did not fit, reorganize */
/* If the record did not fit, reorganize */
btr_page_reorganize
(
page
,
index
,
mtr
);
btr_page_reorganize
(
page
,
index
,
mtr
);
...
@@ -1039,7 +1040,7 @@ btr_cur_optimistic_insert(
...
@@ -1039,7 +1040,7 @@ btr_cur_optimistic_insert(
*
rec
=
page_cur_tuple_insert
(
page_cursor
,
entry
,
index
,
mtr
);
*
rec
=
page_cur_tuple_insert
(
page_cursor
,
entry
,
index
,
mtr
);
if
(
!*
rec
)
{
if
(
UNIV_UNLIKELY
(
!*
rec
)
)
{
fputs
(
"InnoDB: Error: cannot insert tuple "
,
stderr
);
fputs
(
"InnoDB: Error: cannot insert tuple "
,
stderr
);
dtuple_print
(
stderr
,
entry
);
dtuple_print
(
stderr
,
entry
);
fputs
(
" into "
,
stderr
);
fputs
(
" into "
,
stderr
);
...
@@ -1166,7 +1167,7 @@ btr_cur_pessimistic_insert(
...
@@ -1166,7 +1167,7 @@ btr_cur_pessimistic_insert(
}
}
if
(
rec_get_converted_size
(
index
,
entry
)
>=
if
(
rec_get_converted_size
(
index
,
entry
)
>=
ut_min
(
page_get_free_space_of_empty
(
index
->
table
->
comp
)
/
2
,
ut_min
(
page_get_free_space_of_empty
(
page_is_comp
(
page
)
)
/
2
,
REC_MAX_DATA_SIZE
))
{
REC_MAX_DATA_SIZE
))
{
/* The record is so big that we have to store some fields
/* The record is so big that we have to store some fields
...
@@ -1293,9 +1294,11 @@ btr_cur_update_in_place_log(
...
@@ -1293,9 +1294,11 @@ btr_cur_update_in_place_log(
mtr_t
*
mtr
)
/* in: mtr */
mtr_t
*
mtr
)
/* in: mtr */
{
{
byte
*
log_ptr
;
byte
*
log_ptr
;
page_t
*
page
=
ut_align_down
(
rec
,
UNIV_PAGE_SIZE
);
ut_ad
(
flags
<
256
);
ut_ad
(
flags
<
256
);
ut_ad
(
!!
page_is_comp
(
page
)
==
index
->
table
->
comp
);
log_ptr
=
mlog_open_and_write_index
(
mtr
,
rec
,
index
,
index
->
table
->
comp
log_ptr
=
mlog_open_and_write_index
(
mtr
,
rec
,
index
,
page_is_comp
(
page
)
?
MLOG_COMP_REC_UPDATE_IN_PLACE
?
MLOG_COMP_REC_UPDATE_IN_PLACE
:
MLOG_REC_UPDATE_IN_PLACE
,
:
MLOG_REC_UPDATE_IN_PLACE
,
1
+
DATA_ROLL_PTR_LEN
+
14
+
2
+
MLOG_BUF_MARGIN
);
1
+
DATA_ROLL_PTR_LEN
+
14
+
2
+
MLOG_BUF_MARGIN
);
...
@@ -1317,7 +1320,7 @@ btr_cur_update_in_place_log(
...
@@ -1317,7 +1320,7 @@ btr_cur_update_in_place_log(
log_ptr
=
row_upd_write_sys_vals_to_log
(
index
,
trx
,
roll_ptr
,
log_ptr
,
log_ptr
=
row_upd_write_sys_vals_to_log
(
index
,
trx
,
roll_ptr
,
log_ptr
,
mtr
);
mtr
);
mach_write_to_2
(
log_ptr
,
rec
-
buf_frame_align
(
rec
));
mach_write_to_2
(
log_ptr
,
ut_align_offset
(
rec
,
UNIV_PAGE_SIZE
));
log_ptr
+=
2
;
log_ptr
+=
2
;
row_upd_index_write_log
(
update
,
log_ptr
,
mtr
);
row_upd_index_write_log
(
update
,
log_ptr
,
mtr
);
...
@@ -1374,18 +1377,11 @@ btr_cur_parse_update_in_place(
...
@@ -1374,18 +1377,11 @@ btr_cur_parse_update_in_place(
ptr
=
row_upd_index_parse
(
ptr
,
end_ptr
,
heap
,
&
update
);
ptr
=
row_upd_index_parse
(
ptr
,
end_ptr
,
heap
,
&
update
);
if
(
ptr
==
NULL
)
{
if
(
!
ptr
||
!
page
)
{
mem_heap_free
(
heap
);
goto
func_exit
;
return
(
NULL
);
}
}
if
(
!
page
)
{
ut_a
(
!!
page_is_comp
(
page
)
==
index
->
table
->
comp
);
mem_heap_free
(
heap
);
return
(
ptr
);
}
rec
=
page
+
rec_offset
;
rec
=
page
+
rec_offset
;
/* We do not need to reserve btr_search_latch, as the page is only
/* We do not need to reserve btr_search_latch, as the page is only
...
@@ -1400,6 +1396,7 @@ btr_cur_parse_update_in_place(
...
@@ -1400,6 +1396,7 @@ btr_cur_parse_update_in_place(
row_upd_rec_in_place
(
rec
,
offsets
,
update
);
row_upd_rec_in_place
(
rec
,
offsets
,
update
);
func_exit:
mem_heap_free
(
heap
);
mem_heap_free
(
heap
);
return
(
ptr
);
return
(
ptr
);
...
@@ -1438,7 +1435,6 @@ btr_cur_update_in_place(
...
@@ -1438,7 +1435,6 @@ btr_cur_update_in_place(
rec
=
btr_cur_get_rec
(
cursor
);
rec
=
btr_cur_get_rec
(
cursor
);
index
=
cursor
->
index
;
index
=
cursor
->
index
;
trx
=
thr_get_trx
(
thr
);
trx
=
thr_get_trx
(
thr
);
heap
=
mem_heap_create
(
100
);
offsets
=
rec_get_offsets
(
rec
,
index
,
offsets
,
ULINT_UNDEFINED
,
&
heap
);
offsets
=
rec_get_offsets
(
rec
,
index
,
offsets
,
ULINT_UNDEFINED
,
&
heap
);
if
(
btr_cur_print_record_ops
&&
thr
)
{
if
(
btr_cur_print_record_ops
&&
thr
)
{
...
@@ -1449,7 +1445,7 @@ btr_cur_update_in_place(
...
@@ -1449,7 +1445,7 @@ btr_cur_update_in_place(
/* Do lock checking and undo logging */
/* Do lock checking and undo logging */
err
=
btr_cur_upd_lock_and_undo
(
flags
,
cursor
,
update
,
cmpl_info
,
err
=
btr_cur_upd_lock_and_undo
(
flags
,
cursor
,
update
,
cmpl_info
,
thr
,
&
roll_ptr
);
thr
,
&
roll_ptr
);
if
(
err
!=
DB_SUCCESS
)
{
if
(
UNIV_UNLIKELY
(
err
!=
DB_SUCCESS
)
)
{
if
(
UNIV_LIKELY_NULL
(
heap
))
{
if
(
UNIV_LIKELY_NULL
(
heap
))
{
mem_heap_free
(
heap
);
mem_heap_free
(
heap
);
...
@@ -1458,6 +1454,8 @@ btr_cur_update_in_place(
...
@@ -1458,6 +1454,8 @@ btr_cur_update_in_place(
}
}
block
=
buf_block_align
(
rec
);
block
=
buf_block_align
(
rec
);
ut_ad
(
!!
page_is_comp
(
buf_block_get_frame
(
block
))
==
index
->
table
->
comp
);
if
(
block
->
is_hashed
)
{
if
(
block
->
is_hashed
)
{
/* The function row_upd_changes_ord_field_binary works only
/* The function row_upd_changes_ord_field_binary works only
...
@@ -1481,7 +1479,8 @@ btr_cur_update_in_place(
...
@@ -1481,7 +1479,8 @@ btr_cur_update_in_place(
/* FIXME: in a mixed tree, all records may not have enough ordering
/* FIXME: in a mixed tree, all records may not have enough ordering
fields for btr search: */
fields for btr search: */
was_delete_marked
=
rec_get_deleted_flag
(
rec
,
index
->
table
->
comp
);
was_delete_marked
=
rec_get_deleted_flag
(
rec
,
page_is_comp
(
buf_block_get_frame
(
block
)));
row_upd_rec_in_place
(
rec
,
offsets
,
update
);
row_upd_rec_in_place
(
rec
,
offsets
,
update
);
...
@@ -1491,7 +1490,8 @@ btr_cur_update_in_place(
...
@@ -1491,7 +1490,8 @@ btr_cur_update_in_place(
btr_cur_update_in_place_log
(
flags
,
rec
,
index
,
update
,
trx
,
roll_ptr
,
btr_cur_update_in_place_log
(
flags
,
rec
,
index
,
update
,
trx
,
roll_ptr
,
mtr
);
mtr
);
if
(
was_delete_marked
&&
!
rec_get_deleted_flag
(
rec
,
index
->
table
->
comp
))
{
if
(
was_delete_marked
&&
!
rec_get_deleted_flag
(
rec
,
page_is_comp
(
buf_block_get_frame
(
block
))))
{
/* The new updated record owns its possible externally
/* The new updated record owns its possible externally
stored fields */
stored fields */
...
@@ -1597,7 +1597,7 @@ btr_cur_optimistic_update(
...
@@ -1597,7 +1597,7 @@ btr_cur_optimistic_update(
new_rec_size
=
rec_get_converted_size
(
index
,
new_entry
);
new_rec_size
=
rec_get_converted_size
(
index
,
new_entry
);
if
(
new_rec_size
>=
if
(
new_rec_size
>=
page_get_free_space_of_empty
(
index
->
table
->
comp
)
/
2
)
{
page_get_free_space_of_empty
(
page_is_comp
(
page
)
)
/
2
)
{
mem_heap_free
(
heap
);
mem_heap_free
(
heap
);
...
@@ -1644,7 +1644,7 @@ btr_cur_optimistic_update(
...
@@ -1644,7 +1644,7 @@ btr_cur_optimistic_update(
explicit locks on rec, before deleting rec (see the comment in
explicit locks on rec, before deleting rec (see the comment in
.._pessimistic_update). */
.._pessimistic_update). */
lock_rec_store_on_page_infimum
(
rec
);
lock_rec_store_on_page_infimum
(
page
,
rec
);
btr_search_update_hash_on_delete
(
cursor
);
btr_search_update_hash_on_delete
(
cursor
);
...
@@ -1665,7 +1665,7 @@ btr_cur_optimistic_update(
...
@@ -1665,7 +1665,7 @@ btr_cur_optimistic_update(
ut_a
(
rec
);
/* <- We calculated above the insert would fit */
ut_a
(
rec
);
/* <- We calculated above the insert would fit */
if
(
!
rec_get_deleted_flag
(
rec
,
index
->
table
->
comp
))
{
if
(
!
rec_get_deleted_flag
(
rec
,
page_is_comp
(
page
)
))
{
/* The new inserted record owns its possible externally
/* The new inserted record owns its possible externally
stored fields */
stored fields */
...
@@ -1814,7 +1814,7 @@ btr_cur_pessimistic_update(
...
@@ -1814,7 +1814,7 @@ btr_cur_pessimistic_update(
}
}
success
=
fsp_reserve_free_extents
(
&
n_reserved
,
success
=
fsp_reserve_free_extents
(
&
n_reserved
,
cursor
->
index
->
space
,
index
->
space
,
n_extents
,
reserve_flag
,
mtr
);
n_extents
,
reserve_flag
,
mtr
);
if
(
!
success
)
{
if
(
!
success
)
{
err
=
DB_OUT_OF_FILE_SPACE
;
err
=
DB_OUT_OF_FILE_SPACE
;
...
@@ -1858,14 +1858,14 @@ btr_cur_pessimistic_update(
...
@@ -1858,14 +1858,14 @@ btr_cur_pessimistic_update(
ext_vect
=
mem_heap_alloc
(
heap
,
sizeof
(
ulint
)
ext_vect
=
mem_heap_alloc
(
heap
,
sizeof
(
ulint
)
*
dict_index_get_n_fields
(
index
));
*
dict_index_get_n_fields
(
index
));
ut_ad
(
!
cursor
->
index
->
table
->
comp
||
!
rec_get_node_ptr_flag
(
rec
));
ut_ad
(
!
page_is_comp
(
page
)
||
!
rec_get_node_ptr_flag
(
rec
));
offsets
=
rec_get_offsets
(
rec
,
index
,
offsets
,
offsets
=
rec_get_offsets
(
rec
,
index
,
offsets
,
ULINT_UNDEFINED
,
&
heap
);
ULINT_UNDEFINED
,
&
heap
);
n_ext_vect
=
btr_push_update_extern_fields
(
ext_vect
,
offsets
,
update
);
n_ext_vect
=
btr_push_update_extern_fields
(
ext_vect
,
offsets
,
update
);
if
(
rec_get_converted_size
(
index
,
new_entry
)
>=
if
(
UNIV_UNLIKELY
(
rec_get_converted_size
(
index
,
new_entry
)
>=
ut_min
(
page_get_free_space_of_empty
(
index
->
table
->
comp
)
/
2
,
ut_min
(
page_get_free_space_of_empty
(
page_is_comp
(
page
)
)
/
2
,
REC_MAX_DATA_SIZE
))
{
REC_MAX_DATA_SIZE
))
)
{
big_rec_vec
=
dtuple_convert_big_rec
(
index
,
new_entry
,
big_rec_vec
=
dtuple_convert_big_rec
(
index
,
new_entry
,
ext_vect
,
n_ext_vect
);
ext_vect
,
n_ext_vect
);
...
@@ -1887,7 +1887,7 @@ btr_cur_pessimistic_update(
...
@@ -1887,7 +1887,7 @@ btr_cur_pessimistic_update(
delete the lock structs set on the root page even if the root
delete the lock structs set on the root page even if the root
page carries just node pointers. */
page carries just node pointers. */
lock_rec_store_on_page_infimum
(
rec
);
lock_rec_store_on_page_infimum
(
buf_frame_align
(
rec
),
rec
);
btr_search_update_hash_on_delete
(
cursor
);
btr_search_update_hash_on_delete
(
cursor
);
...
@@ -1965,8 +1965,7 @@ btr_cur_pessimistic_update(
...
@@ -1965,8 +1965,7 @@ btr_cur_pessimistic_update(
mem_heap_free
(
heap
);
mem_heap_free
(
heap
);
if
(
n_extents
>
0
)
{
if
(
n_extents
>
0
)
{
fil_space_release_free_extents
(
cursor
->
index
->
space
,
fil_space_release_free_extents
(
index
->
space
,
n_reserved
);
n_reserved
);
}
}
*
big_rec
=
big_rec_vec
;
*
big_rec
=
big_rec_vec
;
...
@@ -1995,7 +1994,10 @@ btr_cur_del_mark_set_clust_rec_log(
...
@@ -1995,7 +1994,10 @@ btr_cur_del_mark_set_clust_rec_log(
ut_ad
(
flags
<
256
);
ut_ad
(
flags
<
256
);
ut_ad
(
val
<=
1
);
ut_ad
(
val
<=
1
);
log_ptr
=
mlog_open_and_write_index
(
mtr
,
rec
,
index
,
index
->
table
->
comp
ut_ad
(
!!
page_rec_is_comp
(
rec
)
==
index
->
table
->
comp
);
log_ptr
=
mlog_open_and_write_index
(
mtr
,
rec
,
index
,
page_rec_is_comp
(
rec
)
?
MLOG_COMP_REC_CLUST_DELETE_MARK
?
MLOG_COMP_REC_CLUST_DELETE_MARK
:
MLOG_REC_CLUST_DELETE_MARK
,
:
MLOG_REC_CLUST_DELETE_MARK
,
1
+
1
+
DATA_ROLL_PTR_LEN
+
14
+
2
);
1
+
1
+
DATA_ROLL_PTR_LEN
+
14
+
2
);
...
@@ -2012,7 +2014,7 @@ btr_cur_del_mark_set_clust_rec_log(
...
@@ -2012,7 +2014,7 @@ btr_cur_del_mark_set_clust_rec_log(
log_ptr
=
row_upd_write_sys_vals_to_log
(
index
,
trx
,
roll_ptr
,
log_ptr
,
log_ptr
=
row_upd_write_sys_vals_to_log
(
index
,
trx
,
roll_ptr
,
log_ptr
,
mtr
);
mtr
);
mach_write_to_2
(
log_ptr
,
rec
-
buf_frame_align
(
rec
));
mach_write_to_2
(
log_ptr
,
ut_align_offset
(
rec
,
UNIV_PAGE_SIZE
));
log_ptr
+=
2
;
log_ptr
+=
2
;
mlog_close
(
mtr
,
log_ptr
);
mlog_close
(
mtr
,
log_ptr
);
...
@@ -2039,6 +2041,8 @@ btr_cur_parse_del_mark_set_clust_rec(
...
@@ -2039,6 +2041,8 @@ btr_cur_parse_del_mark_set_clust_rec(
ulint
offset
;
ulint
offset
;
rec_t
*
rec
;
rec_t
*
rec
;
ut_ad
(
!!
page_is_comp
(
page
)
==
index
->
table
->
comp
);
if
(
end_ptr
<
ptr
+
2
)
{
if
(
end_ptr
<
ptr
+
2
)
{
return
(
NULL
);
return
(
NULL
);
...
@@ -2087,7 +2091,7 @@ btr_cur_parse_del_mark_set_clust_rec(
...
@@ -2087,7 +2091,7 @@ btr_cur_parse_del_mark_set_clust_rec(
is only being recovered, and there cannot be a hash index to
is only being recovered, and there cannot be a hash index to
it. */
it. */
rec_set_deleted_flag
(
rec
,
index
->
table
->
comp
,
val
);
rec_set_deleted_flag
(
rec
,
page_is_comp
(
page
)
,
val
);
}
}
return
(
ptr
);
return
(
ptr
);
...
@@ -2161,7 +2165,7 @@ btr_cur_del_mark_set_clust_rec(
...
@@ -2161,7 +2165,7 @@ btr_cur_del_mark_set_clust_rec(
rw_lock_x_lock
(
&
btr_search_latch
);
rw_lock_x_lock
(
&
btr_search_latch
);
}
}
rec_set_deleted_flag
(
rec
,
index
->
table
->
comp
,
val
);
rec_set_deleted_flag
(
rec
,
rec_offs_comp
(
offsets
)
,
val
);
trx
=
thr_get_trx
(
thr
);
trx
=
thr_get_trx
(
thr
);
...
@@ -2486,6 +2490,7 @@ btr_cur_pessimistic_delete(
...
@@ -2486,6 +2490,7 @@ btr_cur_pessimistic_delete(
ulint
n_reserved
;
ulint
n_reserved
;
ibool
success
;
ibool
success
;
ibool
ret
=
FALSE
;
ibool
ret
=
FALSE
;
ulint
level
;
mem_heap_t
*
heap
;
mem_heap_t
*
heap
;
ulint
*
offsets
;
ulint
*
offsets
;
...
@@ -2522,15 +2527,15 @@ btr_cur_pessimistic_delete(
...
@@ -2522,15 +2527,15 @@ btr_cur_pessimistic_delete(
/* Free externally stored fields if the record is neither
/* Free externally stored fields if the record is neither
a node pointer nor in two-byte format.
a node pointer nor in two-byte format.
This avoids an unnecessary loop. */
This avoids an unnecessary loop. */
if
(
cursor
->
index
->
table
->
comp
if
(
page_is_comp
(
page
)
?
!
rec_get_node_ptr_flag
(
rec
)
?
!
rec_get_node_ptr_flag
(
rec
)
:
!
rec_get_1byte_offs_flag
(
rec
))
{
:
!
rec_get_1byte_offs_flag
(
rec
))
{
btr_rec_free_externally_stored_fields
(
cursor
->
index
,
btr_rec_free_externally_stored_fields
(
cursor
->
index
,
rec
,
offsets
,
in_rollback
,
mtr
);
rec
,
offsets
,
in_rollback
,
mtr
);
}
}
if
((
page_get_n_recs
(
page
)
<
2
)
if
(
UNIV_UNLIKELY
(
page_get_n_recs
(
page
)
<
2
)
&&
(
dict_tree_get_page
(
btr_cur_get_tree
(
cursor
))
&&
UNIV_UNLIKELY
(
dict_tree_get_page
(
btr_cur_get_tree
(
cursor
))
!=
buf_frame_get_page_no
(
page
)))
{
!=
buf_frame_get_page_no
(
page
)))
{
/* If there is only one record, drop the whole page in
/* If there is only one record, drop the whole page in
...
@@ -2545,9 +2550,13 @@ btr_cur_pessimistic_delete(
...
@@ -2545,9 +2550,13 @@ btr_cur_pessimistic_delete(
}
}
lock_update_delete
(
rec
);
lock_update_delete
(
rec
);
level
=
btr_page_get_level
(
page
,
mtr
);
if
((
btr_page_get_level
(
page
,
mtr
)
>
0
)
if
(
level
>
0
&&
(
page_rec_get_next
(
page_get_infimum_rec
(
page
))
==
rec
))
{
&&
UNIV_UNLIKELY
(
rec
==
page_rec_get_next
(
page_get_infimum_rec
(
page
))))
{
rec_t
*
next_rec
=
page_rec_get_next
(
rec
);
if
(
btr_page_get_prev
(
page
,
mtr
)
==
FIL_NULL
)
{
if
(
btr_page_get_prev
(
page
,
mtr
)
==
FIL_NULL
)
{
...
@@ -2555,8 +2564,8 @@ btr_cur_pessimistic_delete(
...
@@ -2555,8 +2564,8 @@ btr_cur_pessimistic_delete(
non-leaf level, we must mark the new leftmost node
non-leaf level, we must mark the new leftmost node
pointer as the predefined minimum record */
pointer as the predefined minimum record */
btr_set_min_rec_mark
(
page_rec_get_next
(
rec
),
btr_set_min_rec_mark
(
next_rec
,
page_is_comp
(
page
),
cursor
->
index
->
table
->
comp
,
mtr
);
mtr
);
}
else
{
}
else
{
/* Otherwise, if we delete the leftmost node pointer
/* Otherwise, if we delete the leftmost node pointer
on a page, we have to change the father node pointer
on a page, we have to change the father node pointer
...
@@ -2566,13 +2575,12 @@ btr_cur_pessimistic_delete(
...
@@ -2566,13 +2575,12 @@ btr_cur_pessimistic_delete(
btr_node_ptr_delete
(
tree
,
page
,
mtr
);
btr_node_ptr_delete
(
tree
,
page
,
mtr
);
node_ptr
=
dict_tree_build_node_ptr
(
node_ptr
=
dict_tree_build_node_ptr
(
tree
,
page_rec_get_next
(
rec
)
,
tree
,
next_rec
,
buf_frame_get_page_no
(
page
),
buf_frame_get_page_no
(
page
),
heap
,
btr_page_get_level
(
page
,
mtr
)
);
heap
,
level
);
btr_insert_on_non_leaf_level
(
tree
,
btr_insert_on_non_leaf_level
(
tree
,
btr_page_get_level
(
page
,
mtr
)
+
1
,
level
+
1
,
node_ptr
,
mtr
);
node_ptr
,
mtr
);
}
}
}
}
...
@@ -2812,12 +2820,13 @@ btr_estimate_number_of_different_key_vals(
...
@@ -2812,12 +2820,13 @@ btr_estimate_number_of_different_key_vals(
ulint
add_on
;
ulint
add_on
;
mtr_t
mtr
;
mtr_t
mtr
;
mem_heap_t
*
heap
=
NULL
;
mem_heap_t
*
heap
=
NULL
;
ulint
offsets1_
[
REC_OFFS_NORMAL_SIZE
];
ulint
offsets_rec_
[
REC_OFFS_NORMAL_SIZE
];
ulint
offsets2_
[
REC_OFFS_NORMAL_SIZE
];
ulint
offsets_next_rec_
[
REC_OFFS_NORMAL_SIZE
];
ulint
*
offsets1
=
offsets1_
;
ulint
*
offsets_rec
=
offsets_rec_
;
ulint
*
offsets2
=
offsets2_
;
ulint
*
offsets_next_rec
=
offsets_next_rec_
;
*
offsets1_
=
(
sizeof
offsets1_
)
/
sizeof
*
offsets1_
;
*
offsets_rec_
=
(
sizeof
offsets_rec_
)
/
sizeof
*
offsets_rec_
;
*
offsets2_
=
(
sizeof
offsets2_
)
/
sizeof
*
offsets2_
;
*
offsets_next_rec_
=
(
sizeof
offsets_next_rec_
)
/
sizeof
*
offsets_next_rec_
;
n_cols
=
dict_index_get_n_unique
(
index
);
n_cols
=
dict_index_get_n_unique
(
index
);
...
@@ -2830,6 +2839,7 @@ btr_estimate_number_of_different_key_vals(
...
@@ -2830,6 +2839,7 @@ btr_estimate_number_of_different_key_vals(
/* We sample some pages in the index to get an estimate */
/* We sample some pages in the index to get an estimate */
for
(
i
=
0
;
i
<
BTR_KEY_VAL_ESTIMATE_N_PAGES
;
i
++
)
{
for
(
i
=
0
;
i
<
BTR_KEY_VAL_ESTIMATE_N_PAGES
;
i
++
)
{
rec_t
*
supremum
;
mtr_start
(
&
mtr
);
mtr_start
(
&
mtr
);
btr_cur_open_at_rnd_pos
(
index
,
BTR_SEARCH_LEAF
,
&
cursor
,
&
mtr
);
btr_cur_open_at_rnd_pos
(
index
,
BTR_SEARCH_LEAF
,
&
cursor
,
&
mtr
);
...
@@ -2842,26 +2852,29 @@ btr_estimate_number_of_different_key_vals(
...
@@ -2842,26 +2852,29 @@ btr_estimate_number_of_different_key_vals(
page
=
btr_cur_get_page
(
&
cursor
);
page
=
btr_cur_get_page
(
&
cursor
);
rec
=
page_get_infi
mum_rec
(
page
);
supremum
=
page_get_supre
mum_rec
(
page
);
rec
=
page_rec_get_next
(
rec
);
rec
=
page_rec_get_next
(
page_get_infimum_rec
(
page
)
);
if
(
rec
!=
page_get_supremum_rec
(
page
)
)
{
if
(
rec
!=
supremum
)
{
not_empty_flag
=
1
;
not_empty_flag
=
1
;
offsets_rec
=
rec_get_offsets
(
rec
,
index
,
offsets_rec
,
ULINT_UNDEFINED
,
&
heap
);
}
}
while
(
rec
!=
page_get_supremum_rec
(
page
)
while
(
rec
!=
supremum
)
{
&&
page_rec_get_next
(
rec
)
!=
page_get_supremum_rec
(
page
))
{
rec_t
*
next_rec
=
page_rec_get_next
(
rec
);
rec_t
*
next_rec
=
page_rec_get_next
(
rec
);
if
(
next_rec
==
supremum
)
{
break
;
}
matched_fields
=
0
;
matched_fields
=
0
;
matched_bytes
=
0
;
matched_bytes
=
0
;
offsets1
=
rec_get_offsets
(
rec
,
index
,
offsets1
,
offsets_next_rec
=
rec_get_offsets
(
next_rec
,
index
,
ULINT_UNDEFINED
,
&
heap
);
offsets_next_rec
,
offsets2
=
rec_get_offsets
(
next_rec
,
index
,
offsets2
,
n_cols
,
&
heap
);
n_cols
,
&
heap
);
cmp_rec_rec_with_match
(
rec
,
next_rec
,
cmp_rec_rec_with_match
(
rec
,
next_rec
,
offsets
1
,
offsets2
,
offsets
_rec
,
offsets_next_rec
,
index
,
&
matched_fields
,
index
,
&
matched_fields
,
&
matched_bytes
);
&
matched_bytes
);
...
@@ -2874,9 +2887,17 @@ btr_estimate_number_of_different_key_vals(
...
@@ -2874,9 +2887,17 @@ btr_estimate_number_of_different_key_vals(
total_external_size
+=
total_external_size
+=
btr_rec_get_externally_stored_len
(
btr_rec_get_externally_stored_len
(
rec
,
offsets
1
);
rec
,
offsets
_rec
);
rec
=
page_rec_get_next
(
rec
);
rec
=
next_rec
;
/* Initialize offsets_rec for the next round
and assign the old offsets_rec buffer to
offsets_next_rec. */
{
ulint
*
offsets_tmp
=
offsets_rec
;
offsets_rec
=
offsets_next_rec
;
offsets_next_rec
=
offsets_tmp
;
}
}
}
...
@@ -2898,11 +2919,11 @@ btr_estimate_number_of_different_key_vals(
...
@@ -2898,11 +2919,11 @@ btr_estimate_number_of_different_key_vals(
}
}
}
}
offsets
1
=
rec_get_offsets
(
rec
,
index
,
offsets1
,
offsets
_rec
=
rec_get_offsets
(
rec
,
index
,
offsets_rec
,
ULINT_UNDEFINED
,
&
heap
);
ULINT_UNDEFINED
,
&
heap
);
total_external_size
+=
total_external_size
+=
btr_rec_get_externally_stored_len
(
rec
,
btr_rec_get_externally_stored_len
(
rec
,
offsets
1
);
offsets
_rec
);
mtr_commit
(
&
mtr
);
mtr_commit
(
&
mtr
);
}
}
...
@@ -3598,7 +3619,7 @@ btr_rec_free_externally_stored_fields(
...
@@ -3598,7 +3619,7 @@ btr_rec_free_externally_stored_fields(
MTR_MEMO_PAGE_X_FIX
));
MTR_MEMO_PAGE_X_FIX
));
/* Free possible externally stored fields in the record */
/* Free possible externally stored fields in the record */
ut_ad
(
index
->
table
->
comp
==
rec_offs_comp
(
offsets
));
ut_ad
(
index
->
table
->
comp
==
!!
rec_offs_comp
(
offsets
));
n_fields
=
rec_offs_n_fields
(
offsets
);
n_fields
=
rec_offs_n_fields
(
offsets
);
for
(
i
=
0
;
i
<
n_fields
;
i
++
)
{
for
(
i
=
0
;
i
<
n_fields
;
i
++
)
{
...
...
innobase/btr/btr0pcur.c
View file @
b3d6f517
...
@@ -78,6 +78,7 @@ btr_pcur_store_position(
...
@@ -78,6 +78,7 @@ btr_pcur_store_position(
rec_t
*
rec
;
rec_t
*
rec
;
dict_tree_t
*
tree
;
dict_tree_t
*
tree
;
page_t
*
page
;
page_t
*
page
;
ulint
offs
;
ut_a
(
cursor
->
pos_state
==
BTR_PCUR_IS_POSITIONED
);
ut_a
(
cursor
->
pos_state
==
BTR_PCUR_IS_POSITIONED
);
ut_ad
(
cursor
->
latch_mode
!=
BTR_NO_LATCHES
);
ut_ad
(
cursor
->
latch_mode
!=
BTR_NO_LATCHES
);
...
@@ -87,7 +88,8 @@ btr_pcur_store_position(
...
@@ -87,7 +88,8 @@ btr_pcur_store_position(
page_cursor
=
btr_pcur_get_page_cur
(
cursor
);
page_cursor
=
btr_pcur_get_page_cur
(
cursor
);
rec
=
page_cur_get_rec
(
page_cursor
);
rec
=
page_cur_get_rec
(
page_cursor
);
page
=
buf_frame_align
(
rec
);
page
=
ut_align_down
(
rec
,
UNIV_PAGE_SIZE
);
offs
=
ut_align_offset
(
rec
,
UNIV_PAGE_SIZE
);
ut_ad
(
mtr_memo_contains
(
mtr
,
buf_block_align
(
page
),
ut_ad
(
mtr_memo_contains
(
mtr
,
buf_block_align
(
page
),
MTR_MEMO_PAGE_S_FIX
)
MTR_MEMO_PAGE_S_FIX
)
...
@@ -95,35 +97,33 @@ btr_pcur_store_position(
...
@@ -95,35 +97,33 @@ btr_pcur_store_position(
MTR_MEMO_PAGE_X_FIX
));
MTR_MEMO_PAGE_X_FIX
));
ut_a
(
cursor
->
latch_mode
!=
BTR_NO_LATCHES
);
ut_a
(
cursor
->
latch_mode
!=
BTR_NO_LATCHES
);
if
(
page_get_n_recs
(
page
)
==
0
)
{
if
(
UNIV_UNLIKELY
(
page_get_n_recs
(
page
)
==
0
)
)
{
/* It must be an empty index tree; NOTE that in this case
/* It must be an empty index tree; NOTE that in this case
we do not store the modify_clock, but always do a search
we do not store the modify_clock, but always do a search
if we restore the cursor position */
if we restore the cursor position */
ut_a
(
btr_page_get_next
(
page
,
mtr
)
==
FIL_NULL
ut_a
(
btr_page_get_next
(
page
,
mtr
)
==
FIL_NULL
);
&&
btr_page_get_prev
(
page
,
mtr
)
==
FIL_NULL
);
ut_a
(
btr_page_get_prev
(
page
,
mtr
)
==
FIL_NULL
);
if
(
rec
==
page_get_supremum_rec
(
page
))
{
cursor
->
old_stored
=
BTR_PCUR_OLD_STORED
;
cursor
->
rel_pos
=
BTR_PCUR_AFTER_LAST_IN_TREE
;
if
(
page_rec_is_supremum_low
(
offs
))
{
cursor
->
old_stored
=
BTR_PCUR_OLD_STORED
;
return
;
cursor
->
rel_pos
=
BTR_PCUR_AFTER_LAST_IN_TREE
;
}
else
{
cursor
->
rel_pos
=
BTR_PCUR_BEFORE_FIRST_IN_TREE
;
}
}
cursor
->
rel_pos
=
BTR_PCUR_BEFORE_FIRST_IN_TREE
;
cursor
->
old_stored
=
BTR_PCUR_OLD_STORED
;
return
;
return
;
}
}
if
(
rec
==
page_get_supremum_rec
(
page
))
{
if
(
page_rec_is_supremum_low
(
offs
))
{
rec
=
page_rec_get_prev
(
rec
);
rec
=
page_rec_get_prev
(
rec
);
cursor
->
rel_pos
=
BTR_PCUR_AFTER
;
cursor
->
rel_pos
=
BTR_PCUR_AFTER
;
}
else
if
(
rec
==
page_get_infimum_rec
(
page
))
{
}
else
if
(
page_rec_is_infimum_low
(
offs
))
{
rec
=
page_rec_get_next
(
rec
);
rec
=
page_rec_get_next
(
rec
);
...
@@ -139,7 +139,8 @@ btr_pcur_store_position(
...
@@ -139,7 +139,8 @@ btr_pcur_store_position(
&
cursor
->
buf_size
);
&
cursor
->
buf_size
);
cursor
->
block_when_stored
=
buf_block_align
(
page
);
cursor
->
block_when_stored
=
buf_block_align
(
page
);
cursor
->
modify_clock
=
buf_frame_get_modify_clock
(
page
);
cursor
->
modify_clock
=
buf_block_get_modify_clock
(
cursor
->
block_when_stored
);
}
}
/******************************************************************
/******************************************************************
...
@@ -202,12 +203,11 @@ btr_pcur_restore_position(
...
@@ -202,12 +203,11 @@ btr_pcur_restore_position(
dtuple_t
*
tuple
;
dtuple_t
*
tuple
;
ulint
mode
;
ulint
mode
;
ulint
old_mode
;
ulint
old_mode
;
ibool
from_left
;
mem_heap_t
*
heap
;
mem_heap_t
*
heap
;
ut_a
(
cursor
->
pos_state
==
BTR_PCUR_WAS_POSITIONED
ut_a
d
(
cursor
->
pos_state
==
BTR_PCUR_WAS_POSITIONED
||
cursor
->
pos_state
==
BTR_PCUR_IS_POSITIONED
);
||
cursor
->
pos_state
==
BTR_PCUR_IS_POSITIONED
);
if
(
cursor
->
old_stored
!=
BTR_PCUR_OLD_STORED
)
{
if
(
UNIV_UNLIKELY
(
cursor
->
old_stored
!=
BTR_PCUR_OLD_STORED
)
)
{
ut_print_buf
(
stderr
,
(
const
byte
*
)
cursor
,
sizeof
(
btr_pcur_t
));
ut_print_buf
(
stderr
,
(
const
byte
*
)
cursor
,
sizeof
(
btr_pcur_t
));
if
(
cursor
->
trx_if_known
)
{
if
(
cursor
->
trx_if_known
)
{
trx_print
(
stderr
,
cursor
->
trx_if_known
);
trx_print
(
stderr
,
cursor
->
trx_if_known
);
...
@@ -216,19 +216,14 @@ btr_pcur_restore_position(
...
@@ -216,19 +216,14 @@ btr_pcur_restore_position(
ut_a
(
0
);
ut_a
(
0
);
}
}
if
(
cursor
->
rel_pos
==
BTR_PCUR_AFTER_LAST_IN_TREE
if
(
UNIV_UNLIKELY
(
cursor
->
rel_pos
==
BTR_PCUR_AFTER_LAST_IN_TREE
||
cursor
->
rel_pos
==
BTR_PCUR_BEFORE_FIRST_IN_TREE
)
{
||
cursor
->
rel_pos
==
BTR_PCUR_BEFORE_FIRST_IN_TREE
)
)
{
/* In these cases we do not try an optimistic restoration,
/* In these cases we do not try an optimistic restoration,
but always do a search */
but always do a search */
if
(
cursor
->
rel_pos
==
BTR_PCUR_BEFORE_FIRST_IN_TREE
)
{
btr_cur_open_at_index_side
(
from_left
=
TRUE
;
cursor
->
rel_pos
==
BTR_PCUR_BEFORE_FIRST_IN_TREE
,
}
else
{
from_left
=
FALSE
;
}
btr_cur_open_at_index_side
(
from_left
,
btr_pcur_get_btr_cur
(
cursor
)
->
index
,
latch_mode
,
btr_pcur_get_btr_cur
(
cursor
)
->
index
,
latch_mode
,
btr_pcur_get_btr_cur
(
cursor
),
mtr
);
btr_pcur_get_btr_cur
(
cursor
),
mtr
);
...
@@ -238,17 +233,18 @@ btr_pcur_restore_position(
...
@@ -238,17 +233,18 @@ btr_pcur_restore_position(
return
(
FALSE
);
return
(
FALSE
);
}
}
ut_a
(
cursor
->
old_rec
);
ut_a
d
(
cursor
->
old_rec
);
ut_a
(
cursor
->
old_n_fields
);
ut_a
d
(
cursor
->
old_n_fields
);
page
=
btr_cur_get_page
(
btr_pcur_get_btr_cur
(
cursor
));
page
=
btr_cur_get_page
(
btr_pcur_get_btr_cur
(
cursor
));
if
(
latch_mode
==
BTR_SEARCH_LEAF
||
latch_mode
==
BTR_MODIFY_LEAF
)
{
if
(
UNIV_LIKELY
(
latch_mode
==
BTR_SEARCH_LEAF
)
||
UNIV_LIKELY
(
latch_mode
==
BTR_MODIFY_LEAF
))
{
/* Try optimistic restoration */
/* Try optimistic restoration */
if
(
buf_page_optimistic_get
(
latch_mode
,
if
(
UNIV_LIKELY
(
buf_page_optimistic_get
(
latch_mode
,
cursor
->
block_when_stored
,
page
,
cursor
->
block_when_stored
,
page
,
cursor
->
modify_clock
,
mtr
))
{
cursor
->
modify_clock
,
mtr
))
)
{
cursor
->
pos_state
=
BTR_PCUR_IS_POSITIONED
;
cursor
->
pos_state
=
BTR_PCUR_IS_POSITIONED
;
#ifdef UNIV_SYNC_DEBUG
#ifdef UNIV_SYNC_DEBUG
buf_page_dbg_add_level
(
page
,
SYNC_TREE_NODE
);
buf_page_dbg_add_level
(
page
,
SYNC_TREE_NODE
);
...
@@ -297,7 +293,7 @@ btr_pcur_restore_position(
...
@@ -297,7 +293,7 @@ btr_pcur_restore_position(
/* Save the old search mode of the cursor */
/* Save the old search mode of the cursor */
old_mode
=
cursor
->
search_mode
;
old_mode
=
cursor
->
search_mode
;
if
(
cursor
->
rel_pos
==
BTR_PCUR_ON
)
{
if
(
UNIV_LIKELY
(
cursor
->
rel_pos
==
BTR_PCUR_ON
)
)
{
mode
=
PAGE_CUR_LE
;
mode
=
PAGE_CUR_LE
;
}
else
if
(
cursor
->
rel_pos
==
BTR_PCUR_AFTER
)
{
}
else
if
(
cursor
->
rel_pos
==
BTR_PCUR_AFTER
)
{
mode
=
PAGE_CUR_G
;
mode
=
PAGE_CUR_G
;
...
@@ -323,12 +319,10 @@ btr_pcur_restore_position(
...
@@ -323,12 +319,10 @@ btr_pcur_restore_position(
the cursor can now be on a different page! But we can retain
the cursor can now be on a different page! But we can retain
the value of old_rec */
the value of old_rec */
cursor
->
modify_clock
=
buf_frame_get_modify_clock
(
btr_pcur_get_page
(
cursor
));
cursor
->
block_when_stored
=
cursor
->
block_when_stored
=
buf_block_align
(
btr_pcur_get_page
(
cursor
));
buf_block_align
(
btr_pcur_get_page
(
cursor
));
cursor
->
modify_clock
=
buf_block_get_modify_clock
(
cursor
->
block_when_stored
);
cursor
->
old_stored
=
BTR_PCUR_OLD_STORED
;
cursor
->
old_stored
=
BTR_PCUR_OLD_STORED
;
mem_heap_free
(
heap
);
mem_heap_free
(
heap
);
...
...
innobase/btr/btr0sea.c
View file @
b3d6f517
...
@@ -544,7 +544,6 @@ btr_search_check_guess(
...
@@ -544,7 +544,6 @@ btr_search_check_guess(
or PAGE_CUR_GE */
or PAGE_CUR_GE */
mtr_t
*
mtr
)
/* in: mtr */
mtr_t
*
mtr
)
/* in: mtr */
{
{
page_t
*
page
;
rec_t
*
rec
;
rec_t
*
rec
;
rec_t
*
prev_rec
;
rec_t
*
prev_rec
;
rec_t
*
next_rec
;
rec_t
*
next_rec
;
...
@@ -561,7 +560,6 @@ btr_search_check_guess(
...
@@ -561,7 +560,6 @@ btr_search_check_guess(
n_unique
=
dict_index_get_n_unique_in_tree
(
cursor
->
index
);
n_unique
=
dict_index_get_n_unique_in_tree
(
cursor
->
index
);
rec
=
btr_cur_get_rec
(
cursor
);
rec
=
btr_cur_get_rec
(
cursor
);
page
=
buf_frame_align
(
rec
);
ut_ad
(
page_rec_is_user_rec
(
rec
));
ut_ad
(
page_rec_is_user_rec
(
rec
));
...
@@ -612,12 +610,13 @@ btr_search_check_guess(
...
@@ -612,12 +610,13 @@ btr_search_check_guess(
if
((
mode
==
PAGE_CUR_G
)
||
(
mode
==
PAGE_CUR_GE
))
{
if
((
mode
==
PAGE_CUR_G
)
||
(
mode
==
PAGE_CUR_GE
))
{
ut_ad
(
rec
!=
page_get_infimum_rec
(
page
));
ut_ad
(
!
page_rec_is_infimum
(
rec
));
prev_rec
=
page_rec_get_prev
(
rec
);
prev_rec
=
page_rec_get_prev
(
rec
);
if
(
prev_rec
==
page_get_infimum_rec
(
page
))
{
if
(
page_rec_is_infimum
(
prev_rec
))
{
success
=
btr_page_get_prev
(
page
,
mtr
)
==
FIL_NULL
;
success
=
btr_page_get_prev
(
buf_frame_align
(
prev_rec
),
mtr
)
==
FIL_NULL
;
goto
exit_func
;
goto
exit_func
;
}
}
...
@@ -634,12 +633,13 @@ btr_search_check_guess(
...
@@ -634,12 +633,13 @@ btr_search_check_guess(
goto
exit_func
;
goto
exit_func
;
}
}
ut_ad
(
rec
!=
page_get_supremum_rec
(
page
));
ut_ad
(
!
page_rec_is_supremum
(
rec
));
next_rec
=
page_rec_get_next
(
rec
);
next_rec
=
page_rec_get_next
(
rec
);
if
(
next_rec
==
page_get_supremum_rec
(
page
))
{
if
(
page_rec_is_supremum
(
next_rec
))
{
if
(
btr_page_get_next
(
page
,
mtr
)
==
FIL_NULL
)
{
if
(
btr_page_get_next
(
buf_frame_align
(
next_rec
),
mtr
)
==
FIL_NULL
)
{
cursor
->
up_match
=
0
;
cursor
->
up_match
=
0
;
success
=
TRUE
;
success
=
TRUE
;
...
@@ -694,7 +694,6 @@ btr_search_guess_on_hash(
...
@@ -694,7 +694,6 @@ btr_search_guess_on_hash(
buf_block_t
*
block
;
buf_block_t
*
block
;
rec_t
*
rec
;
rec_t
*
rec
;
page_t
*
page
;
page_t
*
page
;
ibool
success
;
ulint
fold
;
ulint
fold
;
ulint
tuple_n_fields
;
ulint
tuple_n_fields
;
dulint
tree_id
;
dulint
tree_id
;
...
@@ -710,7 +709,7 @@ btr_search_guess_on_hash(
...
@@ -710,7 +709,7 @@ btr_search_guess_on_hash(
/* Note that, for efficiency, the struct info may not be protected by
/* Note that, for efficiency, the struct info may not be protected by
any latch here! */
any latch here! */
if
(
info
->
n_hash_potential
==
0
)
{
if
(
UNIV_UNLIKELY
(
info
->
n_hash_potential
==
0
)
)
{
return
(
FALSE
);
return
(
FALSE
);
}
}
...
@@ -720,12 +719,13 @@ btr_search_guess_on_hash(
...
@@ -720,12 +719,13 @@ btr_search_guess_on_hash(
tuple_n_fields
=
dtuple_get_n_fields
(
tuple
);
tuple_n_fields
=
dtuple_get_n_fields
(
tuple
);
if
(
tuple_n_fields
<
cursor
->
n_fields
)
{
if
(
UNIV_UNLIKELY
(
tuple_n_fields
<
cursor
->
n_fields
)
)
{
return
(
FALSE
);
return
(
FALSE
);
}
}
if
((
cursor
->
n_bytes
>
0
)
&&
(
tuple_n_fields
<=
cursor
->
n_fields
))
{
if
(
UNIV_UNLIKELY
(
tuple_n_fields
==
cursor
->
n_fields
)
&&
(
cursor
->
n_bytes
>
0
))
{
return
(
FALSE
);
return
(
FALSE
);
}
}
...
@@ -740,39 +740,31 @@ btr_search_guess_on_hash(
...
@@ -740,39 +740,31 @@ btr_search_guess_on_hash(
cursor
->
fold
=
fold
;
cursor
->
fold
=
fold
;
cursor
->
flag
=
BTR_CUR_HASH
;
cursor
->
flag
=
BTR_CUR_HASH
;
if
(
!
has_search_latch
)
{
if
(
UNIV_LIKELY
(
!
has_search_latch
)
)
{
rw_lock_s_lock
(
&
btr_search_latch
);
rw_lock_s_lock
(
&
btr_search_latch
);
}
}
ut_a
(
btr_search_latch
.
writer
!=
RW_LOCK_EX
);
ut_a
d
(
btr_search_latch
.
writer
!=
RW_LOCK_EX
);
ut_a
(
btr_search_latch
.
reader_count
>
0
);
ut_a
d
(
btr_search_latch
.
reader_count
>
0
);
rec
=
ha_search_and_get_data
(
btr_search_sys
->
hash_index
,
fold
);
rec
=
ha_search_and_get_data
(
btr_search_sys
->
hash_index
,
fold
);
if
(
!
rec
)
{
if
(
UNIV_UNLIKELY
(
!
rec
))
{
if
(
!
has_search_latch
)
{
goto
failure_unlock
;
rw_lock_s_unlock
(
&
btr_search_latch
);
}
goto
failure
;
}
}
page
=
buf_frame_align
(
rec
);
page
=
buf_frame_align
(
rec
);
if
(
!
has_search_latch
)
{
if
(
UNIV_LIKELY
(
!
has_search_latch
)
)
{
success
=
buf_page_get_known_nowait
(
latch_mode
,
page
,
if
(
UNIV_UNLIKELY
(
!
buf_page_get_known_nowait
(
latch_mode
,
page
,
BUF_MAKE_YOUNG
,
BUF_MAKE_YOUNG
,
__FILE__
,
__LINE__
,
__FILE__
,
__LINE__
,
mtr
);
mtr
)))
{
goto
failure_unlock
;
rw_lock_s_unlock
(
&
btr_search_latch
);
if
(
!
success
)
{
goto
failure
;
}
}
rw_lock_s_unlock
(
&
btr_search_latch
);
can_only_compare_to_cursor_rec
=
FALSE
;
can_only_compare_to_cursor_rec
=
FALSE
;
#ifdef UNIV_SYNC_DEBUG
#ifdef UNIV_SYNC_DEBUG
...
@@ -782,8 +774,8 @@ btr_search_guess_on_hash(
...
@@ -782,8 +774,8 @@ btr_search_guess_on_hash(
block
=
buf_block_align
(
page
);
block
=
buf_block_align
(
page
);
if
(
block
->
state
==
BUF_BLOCK_REMOVE_HASH
)
{
if
(
UNIV_UNLIKELY
(
block
->
state
==
BUF_BLOCK_REMOVE_HASH
)
)
{
if
(
!
has_search_latch
)
{
if
(
UNIV_LIKELY
(
!
has_search_latch
)
)
{
btr_leaf_page_release
(
page
,
latch_mode
,
mtr
);
btr_leaf_page_release
(
page
,
latch_mode
,
mtr
);
}
}
...
@@ -791,51 +783,33 @@ btr_search_guess_on_hash(
...
@@ -791,51 +783,33 @@ btr_search_guess_on_hash(
goto
failure
;
goto
failure
;
}
}
ut_a
(
block
->
state
==
BUF_BLOCK_FILE_PAGE
);
ut_a
d
(
block
->
state
==
BUF_BLOCK_FILE_PAGE
);
ut_a
(
page_rec_is_user_rec
(
rec
));
ut_a
d
(
page_rec_is_user_rec
(
rec
));
btr_cur_position
(
index
,
rec
,
cursor
);
btr_cur_position
(
index
,
rec
,
cursor
);
/* Check the validity of the guess within the page */
/* Check the validity of the guess within the page */
if
(
0
!=
ut_dulint_cmp
(
tree_id
,
btr_page_get_index_id
(
page
)))
{
/* If we only have the latch on btr_search_latch, not on the
page, it only protects the columns of the record the cursor
success
=
FALSE
;
is positioned on. We cannot look at the next of the previous
/*
record to determine if our guess for the cursor position is
fprintf(stderr, "Tree id %lu, page index id %lu fold %lu\n",
right. */
ut_dulint_get_low(tree_id),
if
(
UNIV_EXPECT
(
ut_dulint_cmp
(
tree_id
,
btr_page_get_index_id
(
page
)),
0
)
ut_dulint_get_low(btr_page_get_index_id(page)),
||
!
btr_search_check_guess
(
cursor
,
can_only_compare_to_cursor_rec
,
fold);
tuple
,
mode
,
mtr
))
{
*/
if
(
UNIV_LIKELY
(
!
has_search_latch
))
{
}
else
{
/* If we only have the latch on btr_search_latch, not on the
page, it only protects the columns of the record the cursor
is positioned on. We cannot look at the next of the previous
record to determine if our guess for the cursor position is
right. */
success
=
btr_search_check_guess
(
cursor
,
can_only_compare_to_cursor_rec
,
tuple
,
mode
,
mtr
);
}
if
(
!
success
)
{
if
(
!
has_search_latch
)
{
btr_leaf_page_release
(
page
,
latch_mode
,
mtr
);
btr_leaf_page_release
(
page
,
latch_mode
,
mtr
);
}
}
goto
failure
;
goto
failure
;
}
}
if
(
info
->
n_hash_potential
<
BTR_SEARCH_BUILD_LIMIT
+
5
)
{
if
(
UNIV_LIKELY
(
info
->
n_hash_potential
<
BTR_SEARCH_BUILD_LIMIT
+
5
)
)
{
info
->
n_hash_potential
++
;
info
->
n_hash_potential
++
;
}
}
if
(
info
->
last_hash_succ
!=
TRUE
)
{
info
->
last_hash_succ
=
TRUE
;
}
#ifdef notdefined
#ifdef notdefined
/* These lines of code can be used in a debug version to check
/* These lines of code can be used in a debug version to check
the correctness of the searched cursor position: */
the correctness of the searched cursor position: */
...
@@ -843,15 +817,14 @@ btr_search_guess_on_hash(
...
@@ -843,15 +817,14 @@ btr_search_guess_on_hash(
info
->
last_hash_succ
=
FALSE
;
info
->
last_hash_succ
=
FALSE
;
/* Currently, does not work if the following fails: */
/* Currently, does not work if the following fails: */
ut_a
(
!
has_search_latch
);
ut_a
d
(
!
has_search_latch
);
btr_leaf_page_release
(
page
,
latch_mode
,
mtr
);
btr_leaf_page_release
(
page
,
latch_mode
,
mtr
);
btr_cur_search_to_nth_level
(
index
,
0
,
tuple
,
mode
,
latch_mode
,
btr_cur_search_to_nth_level
(
index
,
0
,
tuple
,
mode
,
latch_mode
,
&
cursor2
,
0
,
mtr
);
&
cursor2
,
0
,
mtr
);
if
(
mode
==
PAGE_CUR_GE
if
(
mode
==
PAGE_CUR_GE
&&
btr_cur_get_rec
(
&
cursor2
)
==
page_get_supremum_rec
(
&&
page_rec_is_supremum
(
btr_cur_get_rec
(
&
cursor2
)))
{
buf_frame_align
(
btr_cur_get_rec
(
&
cursor2
))))
{
/* If mode is PAGE_CUR_GE, then the binary search
/* If mode is PAGE_CUR_GE, then the binary search
in the index tree may actually take us to the supremum
in the index tree may actually take us to the supremum
...
@@ -861,22 +834,22 @@ btr_search_guess_on_hash(
...
@@ -861,22 +834,22 @@ btr_search_guess_on_hash(
btr_pcur_open_on_user_rec
(
index
,
tuple
,
mode
,
latch_mode
,
btr_pcur_open_on_user_rec
(
index
,
tuple
,
mode
,
latch_mode
,
&
pcur
,
mtr
);
&
pcur
,
mtr
);
ut_a
(
btr_pcur_get_rec
(
&
pcur
)
==
btr_cur_get_rec
(
cursor
));
ut_a
d
(
btr_pcur_get_rec
(
&
pcur
)
==
btr_cur_get_rec
(
cursor
));
}
else
{
}
else
{
ut_a
(
btr_cur_get_rec
(
&
cursor2
)
==
btr_cur_get_rec
(
cursor
));
ut_a
d
(
btr_cur_get_rec
(
&
cursor2
)
==
btr_cur_get_rec
(
cursor
));
}
}
/* NOTE that it is theoretically possible that the above assertions
/* NOTE that it is theoretically possible that the above assertions
fail if the page of the cursor gets removed from the buffer pool
fail if the page of the cursor gets removed from the buffer pool
meanwhile! Thus it might not be a bug. */
meanwhile! Thus it might not be a bug. */
info
->
last_hash_succ
=
TRUE
;
#endif
#endif
info
->
last_hash_succ
=
TRUE
;
#ifdef UNIV_SEARCH_PERF_STAT
#ifdef UNIV_SEARCH_PERF_STAT
btr_search_n_succ
++
;
btr_search_n_succ
++
;
#endif
#endif
if
(
!
has_search_latch
&&
buf_block_peek_if_too_old
(
block
))
{
if
(
UNIV_LIKELY
(
!
has_search_latch
)
&&
buf_block_peek_if_too_old
(
block
))
{
buf_page_make_young
(
page
);
buf_page_make_young
(
page
);
}
}
...
@@ -889,6 +862,10 @@ btr_search_guess_on_hash(
...
@@ -889,6 +862,10 @@ btr_search_guess_on_hash(
return
(
TRUE
);
return
(
TRUE
);
/*-------------------------------------------*/
/*-------------------------------------------*/
failure_unlock:
if
(
UNIV_LIKELY
(
!
has_search_latch
))
{
rw_lock_s_unlock
(
&
btr_search_latch
);
}
failure:
failure:
info
->
n_hash_fail
++
;
info
->
n_hash_fail
++
;
...
@@ -917,7 +894,6 @@ btr_search_drop_page_hash_index(
...
@@ -917,7 +894,6 @@ btr_search_drop_page_hash_index(
ulint
n_fields
;
ulint
n_fields
;
ulint
n_bytes
;
ulint
n_bytes
;
rec_t
*
rec
;
rec_t
*
rec
;
rec_t
*
sup
;
ulint
fold
;
ulint
fold
;
ulint
prev_fold
;
ulint
prev_fold
;
dulint
tree_id
;
dulint
tree_id
;
...
@@ -968,12 +944,10 @@ btr_search_drop_page_hash_index(
...
@@ -968,12 +944,10 @@ btr_search_drop_page_hash_index(
n_cached
=
0
;
n_cached
=
0
;
sup
=
page_get_supremum_rec
(
page
);
rec
=
page_get_infimum_rec
(
page
);
rec
=
page_get_infimum_rec
(
page
);
rec
=
page_rec_get_next
(
rec
);
rec
=
page_rec_get_next
(
rec
);
if
(
rec
!=
sup
)
{
if
(
!
page_rec_is_supremum
(
rec
)
)
{
ut_a
(
n_fields
<=
rec_get_n_fields
(
rec
,
block
->
index
));
ut_a
(
n_fields
<=
rec_get_n_fields
(
rec
,
block
->
index
));
if
(
n_bytes
>
0
)
{
if
(
n_bytes
>
0
)
{
...
@@ -988,7 +962,7 @@ btr_search_drop_page_hash_index(
...
@@ -988,7 +962,7 @@ btr_search_drop_page_hash_index(
heap
=
NULL
;
heap
=
NULL
;
offsets
=
NULL
;
offsets
=
NULL
;
while
(
rec
!=
sup
)
{
while
(
!
page_rec_is_supremum
(
rec
)
)
{
/* FIXME: in a mixed tree, not all records may have enough
/* FIXME: in a mixed tree, not all records may have enough
ordering fields: */
ordering fields: */
offsets
=
rec_get_offsets
(
rec
,
block
->
index
,
offsets
=
rec_get_offsets
(
rec
,
block
->
index
,
...
@@ -1090,7 +1064,6 @@ btr_search_build_page_hash_index(
...
@@ -1090,7 +1064,6 @@ btr_search_build_page_hash_index(
buf_block_t
*
block
;
buf_block_t
*
block
;
rec_t
*
rec
;
rec_t
*
rec
;
rec_t
*
next_rec
;
rec_t
*
next_rec
;
rec_t
*
sup
;
ulint
fold
;
ulint
fold
;
ulint
next_fold
;
ulint
next_fold
;
dulint
tree_id
;
dulint
tree_id
;
...
@@ -1158,15 +1131,13 @@ btr_search_build_page_hash_index(
...
@@ -1158,15 +1131,13 @@ btr_search_build_page_hash_index(
tree_id
=
btr_page_get_index_id
(
page
);
tree_id
=
btr_page_get_index_id
(
page
);
sup
=
page_get_supremum_rec
(
page
);
rec
=
page_get_infimum_rec
(
page
);
rec
=
page_get_infimum_rec
(
page
);
rec
=
page_rec_get_next
(
rec
);
rec
=
page_rec_get_next
(
rec
);
offsets
=
rec_get_offsets
(
rec
,
index
,
offsets
,
offsets
=
rec_get_offsets
(
rec
,
index
,
offsets
,
n_fields
+
(
n_bytes
>
0
),
&
heap
);
n_fields
+
(
n_bytes
>
0
),
&
heap
);
if
(
rec
!=
sup
)
{
if
(
!
page_rec_is_supremum
(
rec
)
)
{
ut_a
(
n_fields
<=
rec_offs_n_fields
(
offsets
));
ut_a
(
n_fields
<=
rec_offs_n_fields
(
offsets
));
if
(
n_bytes
>
0
)
{
if
(
n_bytes
>
0
)
{
...
@@ -1188,7 +1159,7 @@ btr_search_build_page_hash_index(
...
@@ -1188,7 +1159,7 @@ btr_search_build_page_hash_index(
for
(;;)
{
for
(;;)
{
next_rec
=
page_rec_get_next
(
rec
);
next_rec
=
page_rec_get_next
(
rec
);
if
(
next_rec
==
sup
)
{
if
(
page_rec_is_supremum
(
next_rec
)
)
{
if
(
side
==
BTR_SEARCH_RIGHT_SIDE
)
{
if
(
side
==
BTR_SEARCH_RIGHT_SIDE
)
{
...
@@ -1443,7 +1414,6 @@ btr_search_update_hash_on_insert(
...
@@ -1443,7 +1414,6 @@ btr_search_update_hash_on_insert(
{
{
hash_table_t
*
table
;
hash_table_t
*
table
;
buf_block_t
*
block
;
buf_block_t
*
block
;
page_t
*
page
;
rec_t
*
rec
;
rec_t
*
rec
;
rec_t
*
ins_rec
;
rec_t
*
ins_rec
;
rec_t
*
next_rec
;
rec_t
*
next_rec
;
...
@@ -1488,19 +1458,18 @@ btr_search_update_hash_on_insert(
...
@@ -1488,19 +1458,18 @@ btr_search_update_hash_on_insert(
ins_rec
=
page_rec_get_next
(
rec
);
ins_rec
=
page_rec_get_next
(
rec
);
next_rec
=
page_rec_get_next
(
ins_rec
);
next_rec
=
page_rec_get_next
(
ins_rec
);
page
=
buf_frame_align
(
rec
);
offsets
=
rec_get_offsets
(
ins_rec
,
cursor
->
index
,
offsets
,
offsets
=
rec_get_offsets
(
ins_rec
,
cursor
->
index
,
offsets
,
ULINT_UNDEFINED
,
&
heap
);
ULINT_UNDEFINED
,
&
heap
);
ins_fold
=
rec_fold
(
ins_rec
,
offsets
,
n_fields
,
n_bytes
,
tree_id
);
ins_fold
=
rec_fold
(
ins_rec
,
offsets
,
n_fields
,
n_bytes
,
tree_id
);
if
(
next_rec
!=
page_get_supremum_rec
(
page
))
{
if
(
!
page_rec_is_supremum
(
next_rec
))
{
offsets
=
rec_get_offsets
(
next_rec
,
cursor
->
index
,
offsets
,
offsets
=
rec_get_offsets
(
next_rec
,
cursor
->
index
,
offsets
,
n_fields
+
(
n_bytes
>
0
),
&
heap
);
n_fields
+
(
n_bytes
>
0
),
&
heap
);
next_fold
=
rec_fold
(
next_rec
,
offsets
,
n_fields
,
next_fold
=
rec_fold
(
next_rec
,
offsets
,
n_fields
,
n_bytes
,
tree_id
);
n_bytes
,
tree_id
);
}
}
if
(
rec
!=
page_get_infimum_rec
(
page
))
{
if
(
!
page_rec_is_infimum
(
rec
))
{
offsets
=
rec_get_offsets
(
rec
,
cursor
->
index
,
offsets
,
offsets
=
rec_get_offsets
(
rec
,
cursor
->
index
,
offsets
,
n_fields
+
(
n_bytes
>
0
),
&
heap
);
n_fields
+
(
n_bytes
>
0
),
&
heap
);
fold
=
rec_fold
(
rec
,
offsets
,
n_fields
,
n_bytes
,
tree_id
);
fold
=
rec_fold
(
rec
,
offsets
,
n_fields
,
n_bytes
,
tree_id
);
...
@@ -1534,7 +1503,7 @@ btr_search_update_hash_on_insert(
...
@@ -1534,7 +1503,7 @@ btr_search_update_hash_on_insert(
}
}
check_next_rec:
check_next_rec:
if
(
next_rec
==
page_get_supremum_rec
(
page
))
{
if
(
page_rec_is_supremum
(
next_rec
))
{
if
(
side
==
BTR_SEARCH_RIGHT_SIDE
)
{
if
(
side
==
BTR_SEARCH_RIGHT_SIDE
)
{
...
...
innobase/dict/dict0crea.c
View file @
b3d6f517
...
@@ -736,7 +736,7 @@ dict_truncate_index_tree(
...
@@ -736,7 +736,7 @@ dict_truncate_index_tree(
dulint
index_id
;
dulint
index_id
;
byte
*
ptr
;
byte
*
ptr
;
ulint
len
;
ulint
len
;
ibool
comp
;
ulint
comp
;
dict_index_t
*
index
;
dict_index_t
*
index
;
#ifdef UNIV_SYNC_DEBUG
#ifdef UNIV_SYNC_DEBUG
...
...
innobase/ibuf/ibuf0ibuf.c
View file @
b3d6f517
...
@@ -1889,7 +1889,7 @@ ibuf_get_merge_page_nos(
...
@@ -1889,7 +1889,7 @@ ibuf_get_merge_page_nos(
contract the tree, FALSE if this is called
contract the tree, FALSE if this is called
when a single page becomes full and we look
when a single page becomes full and we look
if it pays to read also nearby pages */
if it pays to read also nearby pages */
rec_t
*
first_rec
,
/* in: record from which we read up and down
rec_t
*
rec
,
/* in: record from which we read up and down
in the chain of records */
in the chain of records */
ulint
*
space_ids
,
/* in/out: space id's of the pages */
ulint
*
space_ids
,
/* in/out: space id's of the pages */
ib_longlong
*
space_versions
,
/* in/out: tablespace version
ib_longlong
*
space_versions
,
/* in/out: tablespace version
...
@@ -1907,47 +1907,42 @@ ibuf_get_merge_page_nos(
...
@@ -1907,47 +1907,42 @@ ibuf_get_merge_page_nos(
ulint
first_space_id
;
ulint
first_space_id
;
ulint
rec_page_no
;
ulint
rec_page_no
;
ulint
rec_space_id
;
ulint
rec_space_id
;
rec_t
*
rec
;
ulint
sum_volumes
;
ulint
sum_volumes
;
ulint
volume_for_page
;
ulint
volume_for_page
;
ulint
rec_volume
;
ulint
rec_volume
;
ulint
limit
;
ulint
limit
;
page_t
*
page
;
ulint
n_pages
;
ulint
n_pages
;
*
n_stored
=
0
;
*
n_stored
=
0
;
limit
=
ut_min
(
IBUF_MAX_N_PAGES_MERGED
,
buf_pool
->
curr_size
/
4
);
limit
=
ut_min
(
IBUF_MAX_N_PAGES_MERGED
,
buf_pool
->
curr_size
/
4
);
page
=
buf_frame_align
(
first_rec
);
if
(
page_rec_is_supremum
(
rec
))
{
if
(
first_rec
==
page_get_supremum_rec
(
page
))
{
first_rec
=
page_rec_get_prev
(
first_
rec
);
rec
=
page_rec_get_prev
(
rec
);
}
}
if
(
first_rec
==
page_get_infimum_rec
(
page
))
{
if
(
page_rec_is_infimum
(
rec
))
{
first_rec
=
page_rec_get_next
(
first_
rec
);
rec
=
page_rec_get_next
(
rec
);
}
}
if
(
first_rec
==
page_get_supremum_rec
(
page
))
{
if
(
page_rec_is_supremum
(
rec
))
{
return
(
0
);
return
(
0
);
}
}
rec
=
first_rec
;
first_page_no
=
ibuf_rec_get_page_no
(
rec
);
first_page_no
=
ibuf_rec_get_page_no
(
first_rec
);
first_space_id
=
ibuf_rec_get_space
(
rec
);
first_space_id
=
ibuf_rec_get_space
(
first_rec
);
n_pages
=
0
;
n_pages
=
0
;
prev_page_no
=
0
;
prev_page_no
=
0
;
prev_space_id
=
0
;
prev_space_id
=
0
;
/* Go backwards from the first
_
rec until we reach the border of the
/* Go backwards from the first
rec until we reach the border of the
'merge area', or the page start or the limit of storeable pages is
'merge area', or the page start or the limit of storeable pages is
reached */
reached */
while
(
(
rec
!=
page_get_infimum_rec
(
page
))
&&
(
n_pages
<
limit
))
{
while
(
!
page_rec_is_infimum
(
rec
)
&&
UNIV_LIKELY
(
n_pages
<
limit
))
{
rec_page_no
=
ibuf_rec_get_page_no
(
rec
);
rec_page_no
=
ibuf_rec_get_page_no
(
rec
);
rec_space_id
=
ibuf_rec_get_space
(
rec
);
rec_space_id
=
ibuf_rec_get_space
(
rec
);
...
@@ -1982,7 +1977,7 @@ ibuf_get_merge_page_nos(
...
@@ -1982,7 +1977,7 @@ ibuf_get_merge_page_nos(
volume_for_page
=
0
;
volume_for_page
=
0
;
while
(
*
n_stored
<
limit
)
{
while
(
*
n_stored
<
limit
)
{
if
(
rec
==
page_get_supremum_rec
(
page
))
{
if
(
page_rec_is_supremum
(
rec
))
{
/* When no more records available, mark this with
/* When no more records available, mark this with
another 'impossible' pair of space id, page no */
another 'impossible' pair of space id, page no */
rec_page_no
=
1
;
rec_page_no
=
1
;
...
@@ -2311,12 +2306,12 @@ ibuf_get_volume_buffered(
...
@@ -2311,12 +2306,12 @@ ibuf_get_volume_buffered(
page
=
buf_frame_align
(
rec
);
page
=
buf_frame_align
(
rec
);
if
(
rec
==
page_get_supremum_rec
(
page
))
{
if
(
page_rec_is_supremum
(
rec
))
{
rec
=
page_rec_get_prev
(
rec
);
rec
=
page_rec_get_prev
(
rec
);
}
}
for
(;;)
{
for
(;;)
{
if
(
rec
==
page_get_infimum_rec
(
page
))
{
if
(
page_rec_is_infimum
(
rec
))
{
break
;
break
;
}
}
...
@@ -2351,7 +2346,7 @@ ibuf_get_volume_buffered(
...
@@ -2351,7 +2346,7 @@ ibuf_get_volume_buffered(
rec
=
page_rec_get_prev
(
rec
);
rec
=
page_rec_get_prev
(
rec
);
for
(;;)
{
for
(;;)
{
if
(
rec
==
page_get_infimum_rec
(
prev_page
))
{
if
(
page_rec_is_infimum
(
rec
))
{
/* We cannot go to yet a previous page, because we
/* We cannot go to yet a previous page, because we
do not have the x-latch on it, and cannot acquire one
do not have the x-latch on it, and cannot acquire one
...
@@ -2374,12 +2369,12 @@ ibuf_get_volume_buffered(
...
@@ -2374,12 +2369,12 @@ ibuf_get_volume_buffered(
count_later:
count_later:
rec
=
btr_pcur_get_rec
(
pcur
);
rec
=
btr_pcur_get_rec
(
pcur
);
if
(
rec
!=
page_get_supremum_rec
(
page
))
{
if
(
!
page_rec_is_supremum
(
rec
))
{
rec
=
page_rec_get_next
(
rec
);
rec
=
page_rec_get_next
(
rec
);
}
}
for
(;;)
{
for
(;;)
{
if
(
rec
==
page_get_supremum_rec
(
page
))
{
if
(
page_rec_is_supremum
(
rec
))
{
break
;
break
;
}
}
...
@@ -2414,7 +2409,7 @@ ibuf_get_volume_buffered(
...
@@ -2414,7 +2409,7 @@ ibuf_get_volume_buffered(
rec
=
page_rec_get_next
(
rec
);
rec
=
page_rec_get_next
(
rec
);
for
(;;)
{
for
(;;)
{
if
(
rec
==
page_get_supremum_rec
(
next_page
))
{
if
(
page_rec_is_supremum
(
rec
))
{
/* We give up */
/* We give up */
...
@@ -2815,7 +2810,7 @@ ibuf_insert_to_index_page(
...
@@ -2815,7 +2810,7 @@ ibuf_insert_to_index_page(
ut_ad
(
ibuf_inside
());
ut_ad
(
ibuf_inside
());
ut_ad
(
dtuple_check_typed
(
entry
));
ut_ad
(
dtuple_check_typed
(
entry
));
if
(
index
->
table
->
comp
!=
page_is_comp
(
page
))
{
if
(
UNIV_UNLIKELY
(
index
->
table
->
comp
!=
!!
page_is_comp
(
page
)
))
{
fputs
(
fputs
(
"InnoDB: Trying to insert a record from the insert buffer to an index page
\n
"
"InnoDB: Trying to insert a record from the insert buffer to an index page
\n
"
"InnoDB: but the 'compact' flag does not match!
\n
"
,
stderr
);
"InnoDB: but the 'compact' flag does not match!
\n
"
,
stderr
);
...
@@ -2824,7 +2819,8 @@ ibuf_insert_to_index_page(
...
@@ -2824,7 +2819,8 @@ ibuf_insert_to_index_page(
rec
=
page_rec_get_next
(
page_get_infimum_rec
(
page
));
rec
=
page_rec_get_next
(
page_get_infimum_rec
(
page
));
if
(
rec_get_n_fields
(
rec
,
index
)
!=
dtuple_get_n_fields
(
entry
))
{
if
(
UNIV_UNLIKELY
(
rec_get_n_fields
(
rec
,
index
)
!=
dtuple_get_n_fields
(
entry
)))
{
fputs
(
fputs
(
"InnoDB: Trying to insert a record from the insert buffer to an index page
\n
"
"InnoDB: Trying to insert a record from the insert buffer to an index page
\n
"
"InnoDB: but the number of fields does not match!
\n
"
,
stderr
);
"InnoDB: but the number of fields does not match!
\n
"
,
stderr
);
...
@@ -2861,8 +2857,8 @@ ibuf_insert_to_index_page(
...
@@ -2861,8 +2857,8 @@ ibuf_insert_to_index_page(
PAGE_CUR_LE
,
&
page_cur
);
PAGE_CUR_LE
,
&
page_cur
);
/* This time the record must fit */
/* This time the record must fit */
if
(
!
page_cur_tuple_insert
(
&
page_cur
,
entry
,
if
(
UNIV_UNLIKELY
(
!
page_cur_tuple_insert
(
index
,
mtr
))
{
&
page_cur
,
entry
,
index
,
mtr
)
))
{
ut_print_timestamp
(
stderr
);
ut_print_timestamp
(
stderr
);
...
...
innobase/include/btr0btr.h
View file @
b3d6f517
...
@@ -168,7 +168,7 @@ btr_create(
...
@@ -168,7 +168,7 @@ btr_create(
ulint
type
,
/* in: type of the index */
ulint
type
,
/* in: type of the index */
ulint
space
,
/* in: space where created */
ulint
space
,
/* in: space where created */
dulint
index_id
,
/* in: index id */
dulint
index_id
,
/* in: index id */
ibool
comp
,
/* in: TRUE
=compact page format */
ulint
comp
,
/* in: nonzero
=compact page format */
mtr_t
*
mtr
);
/* in: mini-transaction handle */
mtr_t
*
mtr
);
/* in: mini-transaction handle */
/****************************************************************
/****************************************************************
Frees a B-tree except the root page, which MUST be freed after this
Frees a B-tree except the root page, which MUST be freed after this
...
@@ -276,7 +276,7 @@ void
...
@@ -276,7 +276,7 @@ void
btr_set_min_rec_mark
(
btr_set_min_rec_mark
(
/*=================*/
/*=================*/
rec_t
*
rec
,
/* in: record */
rec_t
*
rec
,
/* in: record */
ibool
comp
,
/* in: TRUE
=compact page format */
ulint
comp
,
/* in: nonzero
=compact page format */
mtr_t
*
mtr
);
/* in: mtr */
mtr_t
*
mtr
);
/* in: mtr */
/*****************************************************************
/*****************************************************************
Deletes on the upper level the node pointer to a page. */
Deletes on the upper level the node pointer to a page. */
...
@@ -336,7 +336,7 @@ btr_parse_set_min_rec_mark(
...
@@ -336,7 +336,7 @@ btr_parse_set_min_rec_mark(
/* out: end of log record or NULL */
/* out: end of log record or NULL */
byte
*
ptr
,
/* in: buffer */
byte
*
ptr
,
/* in: buffer */
byte
*
end_ptr
,
/* in: buffer end */
byte
*
end_ptr
,
/* in: buffer end */
ibool
comp
,
/* in: TRUE
=compact page format */
ulint
comp
,
/* in: nonzero
=compact page format */
page_t
*
page
,
/* in: page or NULL */
page_t
*
page
,
/* in: page or NULL */
mtr_t
*
mtr
);
/* in: mtr or NULL */
mtr_t
*
mtr
);
/* in: mtr or NULL */
/***************************************************************
/***************************************************************
...
...
innobase/include/buf0buf.h
View file @
b3d6f517
...
@@ -382,10 +382,10 @@ Returns the value of the modify clock. The caller must have an s-lock
...
@@ -382,10 +382,10 @@ Returns the value of the modify clock. The caller must have an s-lock
or x-lock on the block. */
or x-lock on the block. */
UNIV_INLINE
UNIV_INLINE
dulint
dulint
buf_
frame
_get_modify_clock
(
buf_
block
_get_modify_clock
(
/*=======================*/
/*=======================*/
/* out: value */
/* out: value */
buf_
frame_t
*
frame
);
/* in: pointer to a frame
*/
buf_
block_t
*
block
);
/* in: block
*/
/************************************************************************
/************************************************************************
Calculates a page checksum which is stored to the page when it is written
Calculates a page checksum which is stored to the page when it is written
to a file. Note that we must be careful to calculate the same value
to a file. Note that we must be careful to calculate the same value
...
...
innobase/include/buf0buf.ic
View file @
b3d6f517
...
@@ -481,17 +481,11 @@ Returns the value of the modify clock. The caller must have an s-lock
...
@@ -481,17 +481,11 @@ Returns the value of the modify clock. The caller must have an s-lock
or x-lock on the block. */
or x-lock on the block. */
UNIV_INLINE
UNIV_INLINE
dulint
dulint
buf_
frame
_get_modify_clock(
buf_
block
_get_modify_clock(
/*=======================*/
/*=======================*/
/* out: value */
/* out: value */
buf_
frame_t* frame) /* in: pointer to a frame
*/
buf_
block_t* block) /* in: block
*/
{
{
buf_block_t* block;
ut_ad(frame);
block = buf_block_align(frame);
#ifdef UNIV_SYNC_DEBUG
#ifdef UNIV_SYNC_DEBUG
ut_ad(rw_lock_own(&(block->lock), RW_LOCK_SHARED)
ut_ad(rw_lock_own(&(block->lock), RW_LOCK_SHARED)
|| rw_lock_own(&(block->lock), RW_LOCK_EXCLUSIVE));
|| rw_lock_own(&(block->lock), RW_LOCK_EXCLUSIVE));
...
...
innobase/include/lock0lock.h
View file @
b3d6f517
...
@@ -216,6 +216,7 @@ actual record is being moved. */
...
@@ -216,6 +216,7 @@ actual record is being moved. */
void
void
lock_rec_store_on_page_infimum
(
lock_rec_store_on_page_infimum
(
/*===========================*/
/*===========================*/
page_t
*
page
,
/* in: page containing the record */
rec_t
*
rec
);
/* in: record whose lock state is stored
rec_t
*
rec
);
/* in: record whose lock state is stored
on the infimum record of the same page; lock
on the infimum record of the same page; lock
bits are reset on the record */
bits are reset on the record */
...
...
innobase/include/mach0data.h
View file @
b3d6f517
...
@@ -52,6 +52,27 @@ mach_read_from_2(
...
@@ -52,6 +52,27 @@ mach_read_from_2(
/*=============*/
/*=============*/
/* out: ulint integer, >= 0, < 64k */
/* out: ulint integer, >= 0, < 64k */
byte
*
b
);
/* in: pointer to two bytes */
byte
*
b
);
/* in: pointer to two bytes */
/************************************************************
The following function is used to convert a 16-bit data item
to the canonical format, for fast bytewise equality test
against memory. */
UNIV_INLINE
uint16
mach_encode_2
(
/*==========*/
/* out: 16-bit integer in canonical format */
ulint
n
);
/* in: integer in machine-dependent format */
/************************************************************
The following function is used to convert a 16-bit data item
from the canonical format, for fast bytewise equality test
against memory. */
UNIV_INLINE
ulint
mach_decode_2
(
/*==========*/
/* out: integer in machine-dependent format */
uint16
n
);
/* in: 16-bit integer in canonical format */
/***********************************************************
/***********************************************************
The following function is used to store data in 3 consecutive
The following function is used to store data in 3 consecutive
bytes. We store the most significant byte to the lowest address. */
bytes. We store the most significant byte to the lowest address. */
...
...
innobase/include/mach0data.ic
View file @
b3d6f517
...
@@ -68,6 +68,37 @@ mach_read_from_2(
...
@@ -68,6 +68,37 @@ mach_read_from_2(
);
);
}
}
/************************************************************
The following function is used to convert a 16-bit data item
to the canonical format, for fast bytewise equality test
against memory. */
UNIV_INLINE
uint16
mach_encode_2(
/*==========*/
/* out: 16-bit integer in canonical format */
ulint n) /* in: integer in machine-dependent format */
{
uint16 ret;
ut_ad(2 == sizeof ret);
mach_write_to_2((byte*) &ret, n);
return(ret);
}
/************************************************************
The following function is used to convert a 16-bit data item
from the canonical format, for fast bytewise equality test
against memory. */
UNIV_INLINE
ulint
mach_decode_2(
/*==========*/
/* out: integer in machine-dependent format */
uint16 n) /* in: 16-bit integer in canonical format */
{
ut_ad(2 == sizeof n);
return(mach_read_from_2((byte*) &n));
}
/***********************************************************
/***********************************************************
The following function is used to store data in 3 consecutive
The following function is used to store data in 3 consecutive
bytes. We store the most significant byte to the lowest address. */
bytes. We store the most significant byte to the lowest address. */
...
...
innobase/include/page0cur.h
View file @
b3d6f517
...
@@ -78,16 +78,16 @@ UNIV_INLINE
...
@@ -78,16 +78,16 @@ UNIV_INLINE
ibool
ibool
page_cur_is_before_first
(
page_cur_is_before_first
(
/*=====================*/
/*=====================*/
/* out: TRUE if at start */
/* out: TRUE if at start */
page_cur_t
*
cur
);
/* in: cursor */
const
page_cur_t
*
cur
);
/* in: cursor */
/*************************************************************
/*************************************************************
Returns TRUE if the cursor is after last user record. */
Returns TRUE if the cursor is after last user record. */
UNIV_INLINE
UNIV_INLINE
ibool
ibool
page_cur_is_after_last
(
page_cur_is_after_last
(
/*===================*/
/*===================*/
/* out: TRUE if at end */
/* out: TRUE if at end */
page_cur_t
*
cur
);
/* in: cursor */
const
page_cur_t
*
cur
);
/* in: cursor */
/**************************************************************
/**************************************************************
Positions the cursor on the given record. */
Positions the cursor on the given record. */
UNIV_INLINE
UNIV_INLINE
...
...
innobase/include/page0cur.ic
View file @
b3d6f517
...
@@ -69,15 +69,10 @@ UNIV_INLINE
...
@@ -69,15 +69,10 @@ UNIV_INLINE
ibool
ibool
page_cur_is_before_first(
page_cur_is_before_first(
/*=====================*/
/*=====================*/
/* out: TRUE if at start */
/* out: TRUE if at start */
page_cur_t* cur) /* in: cursor */
const
page_cur_t* cur) /* in: cursor */
{
{
if (page_get_infimum_rec(page_cur_get_page(cur)) == cur->rec) {
return(page_rec_is_infimum(cur->rec));
return(TRUE);
}
return(FALSE);
}
}
/*************************************************************
/*************************************************************
...
@@ -86,15 +81,10 @@ UNIV_INLINE
...
@@ -86,15 +81,10 @@ UNIV_INLINE
ibool
ibool
page_cur_is_after_last(
page_cur_is_after_last(
/*===================*/
/*===================*/
/* out: TRUE if at end */
/* out: TRUE if at end */
page_cur_t* cur) /* in: cursor */
const
page_cur_t* cur) /* in: cursor */
{
{
if (page_get_supremum_rec(page_cur_get_page(cur)) == cur->rec) {
return(page_rec_is_supremum(cur->rec));
return(TRUE);
}
return(FALSE);
}
}
/**************************************************************
/**************************************************************
...
...
innobase/include/page0page.h
View file @
b3d6f517
...
@@ -373,13 +373,21 @@ page_dir_find_owner_slot(
...
@@ -373,13 +373,21 @@ page_dir_find_owner_slot(
/****************************************************************
/****************************************************************
Determine whether the page is in new-style compact format. */
Determine whether the page is in new-style compact format. */
UNIV_INLINE
UNIV_INLINE
ibool
ulint
page_is_comp
(
page_is_comp
(
/*=========*/
/*=========*/
/* out:
TRUE if the page is in compact forma
t
/* out:
nonzero if the page is in compac
t
FALSE
if it is in old-style format */
format, zero
if it is in old-style format */
page_t
*
page
);
/* in: index page */
page_t
*
page
);
/* in: index page */
/****************************************************************
/****************************************************************
TRUE if the record is on a page in compact format. */
UNIV_INLINE
ulint
page_rec_is_comp
(
/*=============*/
/* out: nonzero if in compact format */
const
rec_t
*
rec
);
/* in: record */
/****************************************************************
Gets the pointer to the next record on the page. */
Gets the pointer to the next record on the page. */
UNIV_INLINE
UNIV_INLINE
rec_t
*
rec_t
*
...
@@ -407,47 +415,55 @@ page_rec_get_prev(
...
@@ -407,47 +415,55 @@ page_rec_get_prev(
/* out: pointer to previous record */
/* out: pointer to previous record */
rec_t
*
rec
);
/* in: pointer to record,
rec_t
*
rec
);
/* in: pointer to record,
must not be page infimum */
must not be page infimum */
/****************************************************************
/****************************************************************
TRUE if the record is a user record on the page. */
TRUE if the record is a user record on the page. */
UNIV_INLINE
UNIV_INLINE
ibool
ibool
page_rec_is_user_rec
(
page_rec_is_user_rec
_low
(
/*=================*/
/*=================
====
*/
/* out: TRUE if a user record */
/* out: TRUE if a user record */
rec_t
*
rec
);
/* in: record
*/
ulint
offset
);
/* in: record offset on page
*/
/****************************************************************
/****************************************************************
TRUE if the record is the supremum record on a page. */
TRUE if the record is the supremum record on a page. */
UNIV_INLINE
UNIV_INLINE
ibool
ibool
page_rec_is_supremum
(
page_rec_is_supremum
_low
(
/*=================*/
/*=================
====
*/
/* out: TRUE if the supremum record */
/* out: TRUE if the supremum record */
rec_t
*
rec
);
/* in: record
*/
ulint
offset
);
/* in: record offset on page
*/
/****************************************************************
/****************************************************************
TRUE if the record is the infimum record on a page. */
TRUE if the record is the infimum record on a page. */
UNIV_INLINE
UNIV_INLINE
ibool
ibool
page_rec_is_infimum
(
page_rec_is_infimum
_low
(
/*================*/
/*================
=====
*/
/* out: TRUE if the infimum record */
/* out: TRUE if the infimum record */
rec_t
*
rec
);
/* in: record */
ulint
offset
);
/* in: record offset on page */
/****************************************************************
/****************************************************************
TRUE if the record is
the first
user record on the page. */
TRUE if the record is
a
user record on the page. */
UNIV_INLINE
UNIV_INLINE
ibool
ibool
page_rec_is_
first_
user_rec
(
page_rec_is_user_rec
(
/*=================
======
*/
/*=================*/
/* out: TRUE if first
user record */
/* out: TRUE if a
user record */
rec_t
*
rec
);
/* in: record */
const
rec_t
*
rec
);
/* in: record */
/****************************************************************
/****************************************************************
TRUE if the record is the
last user record on the
page. */
TRUE if the record is the
supremum record on a
page. */
UNIV_INLINE
UNIV_INLINE
ibool
ibool
page_rec_is_last_user_rec
(
page_rec_is_supremum
(
/*======================*/
/*=================*/
/* out: TRUE if last user record */
/* out: TRUE if the supremum record */
rec_t
*
rec
);
/* in: record */
const
rec_t
*
rec
);
/* in: record */
/****************************************************************
TRUE if the record is the infimum record on a page. */
UNIV_INLINE
ibool
page_rec_is_infimum
(
/*================*/
/* out: TRUE if the infimum record */
const
rec_t
*
rec
);
/* in: record */
/*******************************************************************
/*******************************************************************
Looks for the record which owns the given record. */
Looks for the record which owns the given record. */
UNIV_INLINE
UNIV_INLINE
...
@@ -495,7 +511,7 @@ ulint
...
@@ -495,7 +511,7 @@ ulint
page_get_free_space_of_empty
(
page_get_free_space_of_empty
(
/*=========================*/
/*=========================*/
/* out: free space */
/* out: free space */
ibool
comp
)
/* in: TRUE
=compact page format */
ulint
comp
)
/* in: nonzero
=compact page format */
__attribute__
((
const
));
__attribute__
((
const
));
/****************************************************************
/****************************************************************
Returns the sum of the sizes of the records in the record list
Returns the sum of the sizes of the records in the record list
...
@@ -539,7 +555,7 @@ page_create(
...
@@ -539,7 +555,7 @@ page_create(
buf_frame_t
*
frame
,
/* in: a buffer frame where the page is
buf_frame_t
*
frame
,
/* in: a buffer frame where the page is
created */
created */
mtr_t
*
mtr
,
/* in: mini-transaction handle */
mtr_t
*
mtr
,
/* in: mini-transaction handle */
ibool
comp
);
/* in: TRUE
=compact page format */
ulint
comp
);
/* in: nonzero
=compact page format */
/*****************************************************************
/*****************************************************************
Differs from page_copy_rec_list_end, because this function does not
Differs from page_copy_rec_list_end, because this function does not
touch the lock table and max trx id on page. */
touch the lock table and max trx id on page. */
...
@@ -673,7 +689,7 @@ page_parse_create(
...
@@ -673,7 +689,7 @@ page_parse_create(
/* out: end of log record or NULL */
/* out: end of log record or NULL */
byte
*
ptr
,
/* in: buffer */
byte
*
ptr
,
/* in: buffer */
byte
*
end_ptr
,
/* in: buffer end */
byte
*
end_ptr
,
/* in: buffer end */
ibool
comp
,
/* in: TRUE
=compact page format */
ulint
comp
,
/* in: nonzero
=compact page format */
page_t
*
page
,
/* in: page or NULL */
page_t
*
page
,
/* in: page or NULL */
mtr_t
*
mtr
);
/* in: mtr or NULL */
mtr_t
*
mtr
);
/* in: mtr or NULL */
/****************************************************************
/****************************************************************
...
...
innobase/include/page0page.ic
View file @
b3d6f517
...
@@ -155,14 +155,27 @@ page_header_reset_last_insert(
...
@@ -155,14 +155,27 @@ page_header_reset_last_insert(
/****************************************************************
/****************************************************************
Determine whether the page is in new-style compact format. */
Determine whether the page is in new-style compact format. */
UNIV_INLINE
UNIV_INLINE
ibool
ulint
page_is_comp(
page_is_comp(
/*=========*/
/*=========*/
/* out: TRUE if the page is in compact format
/* out: nonzero if the page is in compact
FALSE if it is in old-style format */
format, zero if it is in old-style format */
page_t* page) /* in: index page */
page_t* page) /* in: index page */
{
return(UNIV_EXPECT(page_header_get_field(page, PAGE_N_HEAP) & 0x8000,
0x8000));
}
/****************************************************************
TRUE if the record is on a page in compact format. */
UNIV_INLINE
ulint
page_rec_is_comp(
/*=============*/
/* out: nonzero if in compact format */
const rec_t* rec) /* in: record */
{
{
return(
!!(page_header_get_field(page, PAGE_N_HEAP) & 0x8000
));
return(
page_is_comp(ut_align_down((rec_t*) rec, UNIV_PAGE_SIZE)
));
}
}
/****************************************************************
/****************************************************************
...
@@ -205,112 +218,107 @@ page_get_supremum_rec(
...
@@ -205,112 +218,107 @@ page_get_supremum_rec(
TRUE if the record is a user record on the page. */
TRUE if the record is a user record on the page. */
UNIV_INLINE
UNIV_INLINE
ibool
ibool
page_rec_is_user_rec(
page_rec_is_user_rec
_low
(
/*=================*/
/*=================
====
*/
/* out: TRUE if a user record */
/* out: TRUE if a user record */
rec_t* rec) /* in: record
*/
ulint offset) /* in: record offset on page
*/
{
{
ut_ad(rec);
ut_ad(offset >= PAGE_NEW_INFIMUM);
#if PAGE_OLD_INFIMUM < PAGE_NEW_INFIMUM
if (rec == page_get_supremum_rec(buf_frame_align(rec))) {
# error "PAGE_OLD_INFIMUM < PAGE_NEW_INFIMUM"
#endif
return(FALSE);
#if PAGE_OLD_SUPREMUM < PAGE_NEW_SUPREMUM
}
# error "PAGE_OLD_SUPREMUM < PAGE_NEW_SUPREMUM"
#endif
if (rec == page_get_infimum_rec(buf_frame_align(rec))) {
#if PAGE_NEW_INFIMUM > PAGE_OLD_SUPREMUM
# error "PAGE_NEW_INFIMUM > PAGE_OLD_SUPREMUM"
return(FALSE);
#endif
}
#if PAGE_OLD_INFIMUM > PAGE_NEW_SUPREMUM
# error "PAGE_OLD_INFIMUM > PAGE_NEW_SUPREMUM"
#endif
#if PAGE_NEW_SUPREMUM > PAGE_OLD_SUPREMUM_END
# error "PAGE_NEW_SUPREMUM > PAGE_OLD_SUPREMUM_END"
#endif
#if PAGE_OLD_SUPREMUM > PAGE_NEW_SUPREMUM_END
# error "PAGE_OLD_SUPREMUM > PAGE_NEW_SUPREMUM_END"
#endif
ut_ad(offset <= UNIV_PAGE_SIZE - PAGE_EMPTY_DIR_START);
return(TRUE);
return(UNIV_LIKELY(offset != PAGE_NEW_SUPREMUM)
&& UNIV_LIKELY(offset != PAGE_NEW_INFIMUM)
&& UNIV_LIKELY(offset != PAGE_OLD_INFIMUM)
&& UNIV_LIKELY(offset != PAGE_OLD_SUPREMUM));
}
}
/****************************************************************
/****************************************************************
TRUE if the record is the supremum record on a page. */
TRUE if the record is the supremum record on a page. */
UNIV_INLINE
UNIV_INLINE
ibool
ibool
page_rec_is_supremum(
page_rec_is_supremum
_low
(
/*=================*/
/*=================
====
*/
/* out: TRUE if the supremum record */
/* out: TRUE if the supremum record */
rec_t* rec) /* in: record
*/
ulint offset) /* in: record offset on page
*/
{
{
ut_ad(rec);
ut_ad(offset >= PAGE_NEW_INFIMUM);
ut_ad(offset <= UNIV_PAGE_SIZE - PAGE_EMPTY_DIR_START);
if (rec == page_get_supremum_rec(buf_frame_align(rec))) {
return(UNIV_UNLIKELY(offset == PAGE_NEW_SUPREMUM)
|| UNIV_UNLIKELY(offset == PAGE_OLD_SUPREMUM));
return(TRUE);
}
return(FALSE);
}
}
/****************************************************************
/****************************************************************
TRUE if the record is the infimum record on a page. */
TRUE if the record is the infimum record on a page. */
UNIV_INLINE
UNIV_INLINE
ibool
ibool
page_rec_is_infimum(
page_rec_is_infimum
_low
(
/*================*/
/*================
=====
*/
/* out: TRUE if the infimum record */
/* out: TRUE if the infimum record */
rec_t* rec) /* in: record
*/
ulint offset) /* in: record offset on page
*/
{
{
ut_ad(rec);
ut_ad(offset >= PAGE_NEW_INFIMUM);
ut_ad(offset <= UNIV_PAGE_SIZE - PAGE_EMPTY_DIR_START);
if (rec == page_get_infimum_rec(buf_frame_align(rec))) {
return(TRUE);
}
return(FALSE);
return(UNIV_UNLIKELY(offset == PAGE_NEW_INFIMUM)
|| UNIV_UNLIKELY(offset == PAGE_OLD_INFIMUM));
}
}
/****************************************************************
/****************************************************************
TRUE if the record is
the first
user record on the page. */
TRUE if the record is
a
user record on the page. */
UNIV_INLINE
UNIV_INLINE
ibool
ibool
page_rec_is_
first_
user_rec(
page_rec_is_user_rec(
/*=================
======
*/
/*=================*/
/* out: TRUE if first
user record */
/* out: TRUE if a
user record */
rec_t* rec) /* in: record */
const
rec_t* rec) /* in: record */
{
{
ut_ad(rec);
return(page_rec_is_user_rec_low(
ut_align_offset(rec, UNIV_PAGE_SIZE)));
if (rec == page_get_supremum_rec(buf_frame_align(rec))) {
return(FALSE);
}
if (rec == page_rec_get_next(
page_get_infimum_rec(buf_frame_align(rec)))) {
return(TRUE);
}
return(FALSE);
}
}
/****************************************************************
/****************************************************************
TRUE if the record is the
last user record on the
page. */
TRUE if the record is the
supremum record on a
page. */
UNIV_INLINE
UNIV_INLINE
ibool
ibool
page_rec_is_
last_user_rec
(
page_rec_is_
supremum
(
/*=================
=====
*/
/*=================*/
/* out: TRUE if last user
record */
/* out: TRUE if the supremum
record */
rec_t* rec) /* in: record */
const
rec_t* rec) /* in: record */
{
{
ut_ad(rec);
return(page_rec_is_supremum_low(
ut_align_offset(rec, UNIV_PAGE_SIZE)));
if (rec == page_get_supremum_rec(buf_frame_align(rec))) {
}
return(FALSE);
}
if (page_rec_get_next(rec)
== page_get_supremum_rec(buf_frame_align(rec))) {
return(TRUE);
}
return(FALSE);
/****************************************************************
TRUE if the record is the infimum record on a page. */
UNIV_INLINE
ibool
page_rec_is_infimum(
/*================*/
/* out: TRUE if the infimum record */
const rec_t* rec) /* in: record */
{
return(page_rec_is_infimum_low(
ut_align_offset(rec, UNIV_PAGE_SIZE)));
}
}
/*****************************************************************
/*****************************************************************
...
@@ -340,22 +348,26 @@ page_cmp_dtuple_rec_with_match(
...
@@ -340,22 +348,26 @@ page_cmp_dtuple_rec_with_match(
matched; when function returns contains the
matched; when function returns contains the
value for current comparison */
value for current comparison */
{
{
page_t* page
;
ulint rec_offset
;
ut_ad(dtuple_check_typed(dtuple));
ut_ad(dtuple_check_typed(dtuple));
ut_ad(rec_offs_validate(rec, NULL, offsets));
ut_ad(rec_offs_validate(rec, NULL, offsets));
ut_ad(!rec_offs_comp(offsets) == !page_rec_is_comp(rec));
page = buf_frame_align(rec);
rec_offset = ut_align_offset(rec, UNIV_PAGE_SIZE);
if (rec == page_get_infimum_rec(page)) {
if (UNIV_UNLIKELY(rec_offset == PAGE_NEW_INFIMUM)
|| UNIV_UNLIKELY(rec_offset == PAGE_OLD_INFIMUM)) {
return(1);
return(1);
} else if (rec == page_get_supremum_rec(page)) {
}
if (UNIV_UNLIKELY(rec_offset == PAGE_NEW_SUPREMUM)
|| UNIV_UNLIKELY(rec_offset == PAGE_OLD_SUPREMUM)) {
return(-1);
return(-1);
} else {
}
return(cmp_dtuple_rec_with_match(dtuple, rec, offsets,
return(cmp_dtuple_rec_with_match(dtuple, rec, offsets,
matched_fields,
matched_fields,
matched_bytes));
matched_bytes));
}
}
}
/*****************************************************************
/*****************************************************************
...
@@ -482,7 +494,7 @@ page_dir_slot_set_rec(
...
@@ -482,7 +494,7 @@ page_dir_slot_set_rec(
{
{
ut_ad(page_rec_check(rec));
ut_ad(page_rec_check(rec));
mach_write_to_2(slot,
rec - buf_frame_align(rec
));
mach_write_to_2(slot,
ut_align_offset(rec, UNIV_PAGE_SIZE
));
}
}
/*******************************************************************
/*******************************************************************
...
@@ -494,8 +506,8 @@ page_dir_slot_get_n_owned(
...
@@ -494,8 +506,8 @@ page_dir_slot_get_n_owned(
/* out: number of records */
/* out: number of records */
page_dir_slot_t* slot) /* in: page directory slot */
page_dir_slot_t* slot) /* in: page directory slot */
{
{
re
turn(rec_get_n_owned(page_dir_slot_get_rec(slot),
re
c_t* rec = page_dir_slot_get_rec(slot);
page_is_comp(buf_frame_align(slot)
)));
return(rec_get_n_owned(rec, page_rec_is_comp(rec
)));
}
}
/*******************************************************************
/*******************************************************************
...
@@ -508,8 +520,8 @@ page_dir_slot_set_n_owned(
...
@@ -508,8 +520,8 @@ page_dir_slot_set_n_owned(
ulint n) /* in: number of records owned
ulint n) /* in: number of records owned
by the slot */
by the slot */
{
{
rec_
set_n_owned(page_dir_slot_get_rec(slot),
rec_
t* rec = page_dir_slot_get_rec(slot);
page_is_comp(buf_frame_align(slot)
), n);
rec_set_n_owned(rec, page_rec_is_comp(rec
), n);
}
}
/****************************************************************
/****************************************************************
...
@@ -540,26 +552,25 @@ page_rec_get_next(
...
@@ -540,26 +552,25 @@ page_rec_get_next(
ut_ad(page_rec_check(rec));
ut_ad(page_rec_check(rec));
page =
buf_frame_align(rec
);
page =
ut_align_down(rec, UNIV_PAGE_SIZE
);
offs = rec_get_next_offs(rec, page_is_comp(page));
offs = rec_get_next_offs(rec, page_is_comp(page));
if (
offs >= UNIV_PAGE_SIZE
) {
if (
UNIV_UNLIKELY(offs >= UNIV_PAGE_SIZE)
) {
fprintf(stderr,
fprintf(stderr,
"InnoDB: Next record offset is nonsensical %lu in record at offset %lu\n",
"InnoDB: Next record offset is nonsensical %lu in record at offset %lu\n"
(ulong)offs, (ulong)(rec - page));
"InnoDB: rec address %p, first buffer frame %p\n"
fprintf(stderr,
"\nInnoDB: rec address %p, first buffer frame %p\n"
"InnoDB: buffer pool high end %p, buf fix count %lu\n",
"InnoDB: buffer pool high end %p, buf fix count %lu\n",
(ulong)offs, (ulong)(rec - page),
rec, buf_pool->frame_zero,
rec, buf_pool->frame_zero,
buf_pool->high_end,
buf_pool->high_end,
(ulong)buf_block_align(rec)->buf_fix_count);
(ulong)buf_block_align(rec)->buf_fix_count);
buf_page_print(page);
buf_page_print(page);
ut_
a(0)
;
ut_
error
;
}
}
if (
offs == 0
) {
if (
UNIV_UNLIKELY(offs == 0)
) {
return(NULL);
return(NULL);
}
}
...
@@ -581,15 +592,12 @@ page_rec_set_next(
...
@@ -581,15 +592,12 @@ page_rec_set_next(
ulint offs;
ulint offs;
ut_ad(page_rec_check(rec));
ut_ad(page_rec_check(rec));
ut_a((next == NULL)
ut_ad(!page_rec_is_supremum(rec));
|| (buf_frame_align(rec) == buf_frame_align(next)));
ut_ad(!page_rec_is_infimum(next));
page = ut_align_down(rec, UNIV_PAGE_SIZE);
page = buf_frame_align(rec);
ut_ad(rec != page_get_supremum_rec(page));
ut_ad(next != page_get_infimum_rec(page));
if (next) {
if (next) {
ut_a(page == ut_align_down(next, UNIV_PAGE_SIZE));
offs = (ulint) (next - page);
offs = (ulint) (next - page);
} else {
} else {
offs = 0;
offs = 0;
...
@@ -613,13 +621,12 @@ page_rec_get_prev(
...
@@ -613,13 +621,12 @@ page_rec_get_prev(
rec_t* rec2;
rec_t* rec2;
rec_t* prev_rec = NULL;
rec_t* prev_rec = NULL;
page_t* page;
page_t* page;
ibool comp;
ut_ad(page_rec_check(rec));
ut_ad(page_rec_check(rec));
page = buf_frame_align(rec);
page = buf_frame_align(rec);
ut_ad(
rec != page_get_infimum_rec(page
));
ut_ad(
!page_rec_is_infimum(rec
));
slot_no = page_dir_find_owner_slot(rec);
slot_no = page_dir_find_owner_slot(rec);
...
@@ -628,7 +635,6 @@ page_rec_get_prev(
...
@@ -628,7 +635,6 @@ page_rec_get_prev(
slot = page_dir_get_nth_slot(page, slot_no - 1);
slot = page_dir_get_nth_slot(page, slot_no - 1);
rec2 = page_dir_slot_get_rec(slot);
rec2 = page_dir_slot_get_rec(slot);
comp = page_is_comp(page);
while (rec != rec2) {
while (rec != rec2) {
prev_rec = rec2;
prev_rec = rec2;
...
@@ -649,13 +655,16 @@ page_rec_find_owner_rec(
...
@@ -649,13 +655,16 @@ page_rec_find_owner_rec(
/* out: the owner record */
/* out: the owner record */
rec_t* rec) /* in: the physical record */
rec_t* rec) /* in: the physical record */
{
{
ibool comp;
ut_ad(page_rec_check(rec));
ut_ad(page_rec_check(rec));
comp = page_is_comp(buf_frame_align(rec));
while (rec_get_n_owned(rec, comp) == 0) {
if (page_rec_is_comp(rec)) {
rec = page_rec_get_next(rec);
while (rec_get_n_owned(rec, TRUE) == 0) {
rec = page_rec_get_next(rec);
}
} else {
while (rec_get_n_owned(rec, FALSE) == 0) {
rec = page_rec_get_next(rec);
}
}
}
return(rec);
return(rec);
...
@@ -691,10 +700,17 @@ ulint
...
@@ -691,10 +700,17 @@ ulint
page_get_free_space_of_empty(
page_get_free_space_of_empty(
/*=========================*/
/*=========================*/
/* out: free space */
/* out: free space */
ibool comp) /* in: TRUE
=compact page layout */
ulint comp) /* in: nonzero
=compact page layout */
{
{
if (UNIV_LIKELY(comp)) {
return((ulint)(UNIV_PAGE_SIZE
- PAGE_NEW_SUPREMUM_END
- PAGE_DIR
- 2 * PAGE_DIR_SLOT_SIZE));
}
return((ulint)(UNIV_PAGE_SIZE
return((ulint)(UNIV_PAGE_SIZE
-
(comp ? PAGE_NEW_SUPREMUM_END : PAGE_OLD_SUPREMUM_END)
-
PAGE_OLD_SUPREMUM_END
- PAGE_DIR
- PAGE_DIR
- 2 * PAGE_DIR_SLOT_SIZE));
- 2 * PAGE_DIR_SLOT_SIZE));
}
}
...
@@ -716,17 +732,21 @@ page_get_max_insert_size(
...
@@ -716,17 +732,21 @@ page_get_max_insert_size(
{
{
ulint occupied;
ulint occupied;
ulint free_space;
ulint free_space;
ibool comp;
comp = page_is_comp(page);
if (page_is_comp(page)) {
occupied = page_header_get_field(page, PAGE_HEAP_TOP)
- PAGE_NEW_SUPREMUM_END + page_dir_calc_reserved_space(
n_recs + page_dir_get_n_heap(page) - 2);
occupied = page_header_get_field(page, PAGE_HEAP_TOP)
free_space = page_get_free_space_of_empty(TRUE);
- (comp ? PAGE_NEW_SUPREMUM_END : PAGE_OLD_SUPREMUM_END)
} else {
+ page_dir_calc_reserved_space(
occupied = page_header_get_field(page, PAGE_HEAP_TOP)
- PAGE_OLD_SUPREMUM_END + page_dir_calc_reserved_space(
n_recs + page_dir_get_n_heap(page) - 2);
n_recs + page_dir_get_n_heap(page) - 2);
free_space = page_get_free_space_of_empty(comp);
free_space = page_get_free_space_of_empty(FALSE);
}
/* Above the 'n_recs +' part reserves directory space for the new
/* Above the 'n_recs +' part reserves directory space for the new
inserted records; the '- 2' excludes page infimum and supremum
inserted records; the '- 2' excludes page infimum and supremum
records */
records */
...
@@ -752,14 +772,11 @@ page_get_max_insert_size_after_reorganize(
...
@@ -752,14 +772,11 @@ page_get_max_insert_size_after_reorganize(
{
{
ulint occupied;
ulint occupied;
ulint free_space;
ulint free_space;
ibool comp;
comp = page_is_comp(page);
occupied = page_get_data_size(page)
occupied = page_get_data_size(page)
+ page_dir_calc_reserved_space(n_recs + page_get_n_recs(page));
+ page_dir_calc_reserved_space(n_recs + page_get_n_recs(page));
free_space = page_get_free_space_of_empty(
comp
);
free_space = page_get_free_space_of_empty(
page_is_comp(page)
);
if (occupied > free_space) {
if (occupied > free_space) {
...
@@ -783,6 +800,7 @@ page_mem_free(
...
@@ -783,6 +800,7 @@ page_mem_free(
ulint garbage;
ulint garbage;
ut_ad(rec_offs_validate(rec, NULL, offsets));
ut_ad(rec_offs_validate(rec, NULL, offsets));
ut_ad(!rec_offs_comp(offsets) == !page_rec_is_comp(rec));
free = page_header_get_ptr(page, PAGE_FREE);
free = page_header_get_ptr(page, PAGE_FREE);
page_rec_set_next(rec, free);
page_rec_set_next(rec, free);
...
...
innobase/include/rem0rec.ic
View file @
b3d6f517
...
@@ -929,14 +929,14 @@ rec_get_nth_field(
...
@@ -929,14 +929,14 @@ rec_get_nth_field(
Determine if the offsets are for a record in the new
Determine if the offsets are for a record in the new
compact format. */
compact format. */
UNIV_INLINE
UNIV_INLINE
ibool
ulint
rec_offs_comp(
rec_offs_comp(
/*==========*/
/*==========*/
/* out:
TRUE
if compact format */
/* out:
nonzero
if compact format */
const ulint* offsets)/* in: array returned by rec_get_offsets() */
const ulint* offsets)/* in: array returned by rec_get_offsets() */
{
{
ut_ad(rec_offs_validate(NULL, NULL, offsets));
ut_ad(rec_offs_validate(NULL, NULL, offsets));
return(
(*rec_offs_base(offsets) & REC_OFFS_COMPACT) != 0
);
return(
*rec_offs_base(offsets) & REC_OFFS_COMPACT
);
}
}
/**********************************************************
/**********************************************************
...
...
innobase/include/row0mysql.h
View file @
b3d6f517
...
@@ -110,7 +110,7 @@ row_mysql_store_col_in_innobase_format(
...
@@ -110,7 +110,7 @@ row_mysql_store_col_in_innobase_format(
necessarily the length of the actual
necessarily the length of the actual
payload data; if the column is a true
payload data; if the column is a true
VARCHAR then this is irrelevant */
VARCHAR then this is irrelevant */
ibool
comp
);
/* in: TRUE =
compact format */
ulint
comp
);
/* in: nonzero=
compact format */
/********************************************************************
/********************************************************************
Handles user errors and lock waits detected by the database engine. */
Handles user errors and lock waits detected by the database engine. */
...
...
innobase/lock/lock0lock.c
View file @
b3d6f517
...
@@ -501,12 +501,7 @@ lock_clust_rec_cons_read_sees(
...
@@ -501,12 +501,7 @@ lock_clust_rec_cons_read_sees(
trx_id
=
row_get_rec_trx_id
(
rec
,
index
,
offsets
);
trx_id
=
row_get_rec_trx_id
(
rec
,
index
,
offsets
);
if
(
read_view_sees_trx_id
(
view
,
trx_id
))
{
return
(
read_view_sees_trx_id
(
view
,
trx_id
));
return
(
TRUE
);
}
return
(
FALSE
);
}
}
/*************************************************************************
/*************************************************************************
...
@@ -1270,7 +1265,6 @@ lock_rec_get_next(
...
@@ -1270,7 +1265,6 @@ lock_rec_get_next(
/*==============*/
/*==============*/
/* out: next lock, NULL if none exists */
/* out: next lock, NULL if none exists */
rec_t
*
rec
,
/* in: record on a page */
rec_t
*
rec
,
/* in: record on a page */
ibool
comp
,
/* in: TRUE=compact page format */
lock_t
*
lock
)
/* in: lock */
lock_t
*
lock
)
/* in: lock */
{
{
#ifdef UNIV_SYNC_DEBUG
#ifdef UNIV_SYNC_DEBUG
...
@@ -1278,19 +1272,19 @@ lock_rec_get_next(
...
@@ -1278,19 +1272,19 @@ lock_rec_get_next(
#endif
/* UNIV_SYNC_DEBUG */
#endif
/* UNIV_SYNC_DEBUG */
ut_ad
(
lock_get_type
(
lock
)
==
LOCK_REC
);
ut_ad
(
lock_get_type
(
lock
)
==
LOCK_REC
);
for
(;;)
{
if
(
page_rec_is_comp
(
rec
))
{
lock
=
lock_rec_get_next_on_page
(
lock
);
do
{
lock
=
lock_rec_get_next_on_page
(
lock
);
if
(
lock
==
NULL
)
{
}
while
(
lock
&&
!
lock_rec_get_nth_bit
(
lock
,
rec_get_heap_no
(
rec
,
TRUE
)));
return
(
NULL
);
}
else
{
}
do
{
lock
=
lock_rec_get_next_on_page
(
lock
);
if
(
lock_rec_get_nth_bit
(
lock
,
rec_get_heap_no
(
rec
,
comp
)))
{
}
while
(
lock
&&
!
lock_rec_get_nth_bit
(
lock
,
rec_get_heap_no
(
rec
,
FALSE
)));
return
(
lock
);
}
}
}
return
(
lock
);
}
}
/*************************************************************************
/*************************************************************************
...
@@ -1303,22 +1297,24 @@ lock_rec_get_first(
...
@@ -1303,22 +1297,24 @@ lock_rec_get_first(
rec_t
*
rec
)
/* in: record on a page */
rec_t
*
rec
)
/* in: record on a page */
{
{
lock_t
*
lock
;
lock_t
*
lock
;
ibool
comp
;
#ifdef UNIV_SYNC_DEBUG
#ifdef UNIV_SYNC_DEBUG
ut_ad
(
mutex_own
(
&
kernel_mutex
));
ut_ad
(
mutex_own
(
&
kernel_mutex
));
#endif
/* UNIV_SYNC_DEBUG */
#endif
/* UNIV_SYNC_DEBUG */
lock
=
lock_rec_get_first_on_page
(
rec
);
lock
=
lock_rec_get_first_on_page
(
rec
);
comp
=
page_is_comp
(
buf_frame_align
(
rec
));
if
(
UNIV_LIKELY_NULL
(
lock
))
{
if
(
page_rec_is_comp
(
rec
))
{
while
(
lock
)
{
while
(
lock
&&
!
lock_rec_get_nth_bit
(
lock
,
if
(
lock_rec_get_nth_bit
(
lock
,
rec_get_heap_no
(
rec
,
comp
)))
{
rec_get_heap_no
(
rec
,
TRUE
)))
{
lock
=
lock_rec_get_next_on_page
(
lock
);
break
;
}
}
else
{
while
(
lock
&&
!
lock_rec_get_nth_bit
(
lock
,
rec_get_heap_no
(
rec
,
FALSE
)))
{
lock
=
lock_rec_get_next_on_page
(
lock
);
}
}
}
lock
=
lock_rec_get_next_on_page
(
lock
);
}
}
return
(
lock
);
return
(
lock
);
...
@@ -1480,7 +1476,6 @@ lock_rec_has_expl(
...
@@ -1480,7 +1476,6 @@ lock_rec_has_expl(
for a supremum record we regard this always a gap
for a supremum record we regard this always a gap
type request */
type request */
rec_t
*
rec
,
/* in: record */
rec_t
*
rec
,
/* in: record */
ibool
comp
,
/* in: TRUE=compact page format */
trx_t
*
trx
)
/* in: transaction */
trx_t
*
trx
)
/* in: transaction */
{
{
lock_t
*
lock
;
lock_t
*
lock
;
...
@@ -1510,7 +1505,7 @@ lock_rec_has_expl(
...
@@ -1510,7 +1505,7 @@ lock_rec_has_expl(
return
(
lock
);
return
(
lock
);
}
}
lock
=
lock_rec_get_next
(
rec
,
comp
,
lock
);
lock
=
lock_rec_get_next
(
rec
,
lock
);
}
}
return
(
NULL
);
return
(
NULL
);
...
@@ -1529,7 +1524,6 @@ lock_rec_other_has_expl_req(
...
@@ -1529,7 +1524,6 @@ lock_rec_other_has_expl_req(
ulint
wait
,
/* in: LOCK_WAIT if also waiting locks are
ulint
wait
,
/* in: LOCK_WAIT if also waiting locks are
taken into account, or 0 if not */
taken into account, or 0 if not */
rec_t
*
rec
,
/* in: record to look at */
rec_t
*
rec
,
/* in: record to look at */
ibool
comp
,
/* in: TRUE=compact record format */
trx_t
*
trx
)
/* in: transaction, or NULL if requests by all
trx_t
*
trx
)
/* in: transaction, or NULL if requests by all
transactions are taken into account */
transactions are taken into account */
{
{
...
@@ -1554,7 +1548,7 @@ lock_rec_other_has_expl_req(
...
@@ -1554,7 +1548,7 @@ lock_rec_other_has_expl_req(
return
(
lock
);
return
(
lock
);
}
}
lock
=
lock_rec_get_next
(
rec
,
comp
,
lock
);
lock
=
lock_rec_get_next
(
rec
,
lock
);
}
}
return
(
NULL
);
return
(
NULL
);
...
@@ -1575,13 +1569,11 @@ lock_rec_other_has_conflicting(
...
@@ -1575,13 +1569,11 @@ lock_rec_other_has_conflicting(
trx_t
*
trx
)
/* in: our transaction */
trx_t
*
trx
)
/* in: our transaction */
{
{
lock_t
*
lock
;
lock_t
*
lock
;
ibool
comp
;
#ifdef UNIV_SYNC_DEBUG
#ifdef UNIV_SYNC_DEBUG
ut_ad
(
mutex_own
(
&
kernel_mutex
));
ut_ad
(
mutex_own
(
&
kernel_mutex
));
#endif
/* UNIV_SYNC_DEBUG */
#endif
/* UNIV_SYNC_DEBUG */
lock
=
lock_rec_get_first
(
rec
);
lock
=
lock_rec_get_first
(
rec
);
comp
=
page_is_comp
(
buf_frame_align
(
rec
));
while
(
lock
)
{
while
(
lock
)
{
if
(
lock_rec_has_to_wait
(
trx
,
mode
,
lock
,
if
(
lock_rec_has_to_wait
(
trx
,
mode
,
lock
,
...
@@ -1590,7 +1582,7 @@ lock_rec_other_has_conflicting(
...
@@ -1590,7 +1582,7 @@ lock_rec_other_has_conflicting(
return
(
lock
);
return
(
lock
);
}
}
lock
=
lock_rec_get_next
(
rec
,
comp
,
lock
);
lock
=
lock_rec_get_next
(
rec
,
lock
);
}
}
return
(
NULL
);
return
(
NULL
);
...
@@ -1616,7 +1608,7 @@ lock_rec_find_similar_on_page(
...
@@ -1616,7 +1608,7 @@ lock_rec_find_similar_on_page(
ut_ad
(
mutex_own
(
&
kernel_mutex
));
ut_ad
(
mutex_own
(
&
kernel_mutex
));
#endif
/* UNIV_SYNC_DEBUG */
#endif
/* UNIV_SYNC_DEBUG */
heap_no
=
rec_get_heap_no
(
rec
,
page_
is_comp
(
buf_frame_align
(
rec
)
));
heap_no
=
rec_get_heap_no
(
rec
,
page_
rec_is_comp
(
rec
));
lock
=
lock_rec_get_first_on_page
(
rec
);
lock
=
lock_rec_get_first_on_page
(
rec
);
while
(
lock
!=
NULL
)
{
while
(
lock
!=
NULL
)
{
...
@@ -1718,6 +1710,8 @@ lock_rec_create(
...
@@ -1718,6 +1710,8 @@ lock_rec_create(
page_no
=
buf_frame_get_page_no
(
page
);
page_no
=
buf_frame_get_page_no
(
page
);
heap_no
=
rec_get_heap_no
(
rec
,
page_is_comp
(
page
));
heap_no
=
rec_get_heap_no
(
rec
,
page_is_comp
(
page
));
ut_ad
(
!!
page_is_comp
(
page
)
==
index
->
table
->
comp
);
/* If rec is the supremum record, then we reset the gap and
/* If rec is the supremum record, then we reset the gap and
LOCK_REC_NOT_GAP bits, as all locks on the supremum are
LOCK_REC_NOT_GAP bits, as all locks on the supremum are
automatically of the gap type */
automatically of the gap type */
...
@@ -1734,7 +1728,7 @@ lock_rec_create(
...
@@ -1734,7 +1728,7 @@ lock_rec_create(
lock
=
mem_heap_alloc
(
trx
->
lock_heap
,
sizeof
(
lock_t
)
+
n_bytes
);
lock
=
mem_heap_alloc
(
trx
->
lock_heap
,
sizeof
(
lock_t
)
+
n_bytes
);
if
(
lock
==
NULL
)
{
if
(
UNIV_UNLIKELY
(
lock
==
NULL
)
)
{
return
(
NULL
);
return
(
NULL
);
}
}
...
@@ -1835,7 +1829,7 @@ lock_rec_enqueue_waiting(
...
@@ -1835,7 +1829,7 @@ lock_rec_enqueue_waiting(
lock_reset_lock_and_trx_wait
(
lock
);
lock_reset_lock_and_trx_wait
(
lock
);
lock_rec_reset_nth_bit
(
lock
,
rec_get_heap_no
(
rec
,
lock_rec_reset_nth_bit
(
lock
,
rec_get_heap_no
(
rec
,
page_
is_comp
(
buf_frame_align
(
rec
)
)));
page_
rec_is_comp
(
rec
)));
return
(
DB_DEADLOCK
);
return
(
DB_DEADLOCK
);
}
}
...
@@ -1885,7 +1879,6 @@ lock_rec_add_to_queue(
...
@@ -1885,7 +1879,6 @@ lock_rec_add_to_queue(
lock_t
*
lock
;
lock_t
*
lock
;
lock_t
*
similar_lock
=
NULL
;
lock_t
*
similar_lock
=
NULL
;
ulint
heap_no
;
ulint
heap_no
;
page_t
*
page
=
buf_frame_align
(
rec
);
ibool
somebody_waits
=
FALSE
;
ibool
somebody_waits
=
FALSE
;
#ifdef UNIV_SYNC_DEBUG
#ifdef UNIV_SYNC_DEBUG
...
@@ -1894,11 +1887,11 @@ lock_rec_add_to_queue(
...
@@ -1894,11 +1887,11 @@ lock_rec_add_to_queue(
ut_ad
((
type_mode
&
(
LOCK_WAIT
|
LOCK_GAP
))
ut_ad
((
type_mode
&
(
LOCK_WAIT
|
LOCK_GAP
))
||
((
type_mode
&
LOCK_MODE_MASK
)
!=
LOCK_S
)
||
((
type_mode
&
LOCK_MODE_MASK
)
!=
LOCK_S
)
||
!
lock_rec_other_has_expl_req
(
LOCK_X
,
0
,
LOCK_WAIT
,
||
!
lock_rec_other_has_expl_req
(
LOCK_X
,
0
,
LOCK_WAIT
,
rec
,
page_is_comp
(
page
),
trx
));
rec
,
trx
));
ut_ad
((
type_mode
&
(
LOCK_WAIT
|
LOCK_GAP
))
ut_ad
((
type_mode
&
(
LOCK_WAIT
|
LOCK_GAP
))
||
((
type_mode
&
LOCK_MODE_MASK
)
!=
LOCK_X
)
||
((
type_mode
&
LOCK_MODE_MASK
)
!=
LOCK_X
)
||
!
lock_rec_other_has_expl_req
(
LOCK_S
,
0
,
LOCK_WAIT
,
||
!
lock_rec_other_has_expl_req
(
LOCK_S
,
0
,
LOCK_WAIT
,
rec
,
page_is_comp
(
page
),
trx
));
rec
,
trx
));
type_mode
=
type_mode
|
LOCK_REC
;
type_mode
=
type_mode
|
LOCK_REC
;
...
@@ -1907,7 +1900,7 @@ lock_rec_add_to_queue(
...
@@ -1907,7 +1900,7 @@ lock_rec_add_to_queue(
try to avoid unnecessary memory consumption of a new record lock
try to avoid unnecessary memory consumption of a new record lock
struct for a gap type lock */
struct for a gap type lock */
if
(
rec
==
page_get_supremum_rec
(
page
))
{
if
(
page_rec_is_supremum
(
rec
))
{
ut_ad
(
!
(
type_mode
&
LOCK_REC_NOT_GAP
));
ut_ad
(
!
(
type_mode
&
LOCK_REC_NOT_GAP
));
/* There should never be LOCK_REC_NOT_GAP on a supremum
/* There should never be LOCK_REC_NOT_GAP on a supremum
...
@@ -1918,7 +1911,7 @@ lock_rec_add_to_queue(
...
@@ -1918,7 +1911,7 @@ lock_rec_add_to_queue(
/* Look for a waiting lock request on the same record or on a gap */
/* Look for a waiting lock request on the same record or on a gap */
heap_no
=
rec_get_heap_no
(
rec
,
page_
is_comp
(
page
));
heap_no
=
rec_get_heap_no
(
rec
,
page_
rec_is_comp
(
rec
));
lock
=
lock_rec_get_first_on_page
(
rec
);
lock
=
lock_rec_get_first_on_page
(
rec
);
while
(
lock
!=
NULL
)
{
while
(
lock
!=
NULL
)
{
...
@@ -1993,7 +1986,7 @@ lock_rec_lock_fast(
...
@@ -1993,7 +1986,7 @@ lock_rec_lock_fast(
||
mode
-
(
LOCK_MODE_MASK
&
mode
)
==
0
||
mode
-
(
LOCK_MODE_MASK
&
mode
)
==
0
||
mode
-
(
LOCK_MODE_MASK
&
mode
)
==
LOCK_REC_NOT_GAP
);
||
mode
-
(
LOCK_MODE_MASK
&
mode
)
==
LOCK_REC_NOT_GAP
);
heap_no
=
rec_get_heap_no
(
rec
,
page_
is_comp
(
buf_frame_align
(
rec
)
));
heap_no
=
rec_get_heap_no
(
rec
,
page_
rec_is_comp
(
rec
));
lock
=
lock_rec_get_first_on_page
(
rec
);
lock
=
lock_rec_get_first_on_page
(
rec
);
...
@@ -2074,8 +2067,7 @@ lock_rec_lock_slow(
...
@@ -2074,8 +2067,7 @@ lock_rec_lock_slow(
trx
=
thr_get_trx
(
thr
);
trx
=
thr_get_trx
(
thr
);
if
(
lock_rec_has_expl
(
mode
,
rec
,
if
(
lock_rec_has_expl
(
mode
,
rec
,
trx
))
{
page_is_comp
(
buf_frame_align
(
rec
)),
trx
))
{
/* The trx already has a strong enough lock on rec: do
/* The trx already has a strong enough lock on rec: do
nothing */
nothing */
...
@@ -2392,14 +2384,12 @@ lock_rec_reset_and_release_wait(
...
@@ -2392,14 +2384,12 @@ lock_rec_reset_and_release_wait(
{
{
lock_t
*
lock
;
lock_t
*
lock
;
ulint
heap_no
;
ulint
heap_no
;
ibool
comp
;
#ifdef UNIV_SYNC_DEBUG
#ifdef UNIV_SYNC_DEBUG
ut_ad
(
mutex_own
(
&
kernel_mutex
));
ut_ad
(
mutex_own
(
&
kernel_mutex
));
#endif
/* UNIV_SYNC_DEBUG */
#endif
/* UNIV_SYNC_DEBUG */
comp
=
page_is_comp
(
buf_frame_align
(
rec
));
heap_no
=
rec_get_heap_no
(
rec
,
page_rec_is_comp
(
rec
));
heap_no
=
rec_get_heap_no
(
rec
,
comp
);
lock
=
lock_rec_get_first
(
rec
);
lock
=
lock_rec_get_first
(
rec
);
...
@@ -2410,7 +2400,7 @@ lock_rec_reset_and_release_wait(
...
@@ -2410,7 +2400,7 @@ lock_rec_reset_and_release_wait(
lock_rec_reset_nth_bit
(
lock
,
heap_no
);
lock_rec_reset_nth_bit
(
lock
,
heap_no
);
}
}
lock
=
lock_rec_get_next
(
rec
,
comp
,
lock
);
lock
=
lock_rec_get_next
(
rec
,
lock
);
}
}
}
}
...
@@ -2428,13 +2418,11 @@ lock_rec_inherit_to_gap(
...
@@ -2428,13 +2418,11 @@ lock_rec_inherit_to_gap(
the locks on this record */
the locks on this record */
{
{
lock_t
*
lock
;
lock_t
*
lock
;
ibool
comp
;
#ifdef UNIV_SYNC_DEBUG
#ifdef UNIV_SYNC_DEBUG
ut_ad
(
mutex_own
(
&
kernel_mutex
));
ut_ad
(
mutex_own
(
&
kernel_mutex
));
#endif
/* UNIV_SYNC_DEBUG */
#endif
/* UNIV_SYNC_DEBUG */
lock
=
lock_rec_get_first
(
rec
);
lock
=
lock_rec_get_first
(
rec
);
comp
=
page_is_comp
(
buf_frame_align
(
rec
));
while
(
lock
!=
NULL
)
{
while
(
lock
!=
NULL
)
{
if
(
!
lock_rec_get_insert_intention
(
lock
))
{
if
(
!
lock_rec_get_insert_intention
(
lock
))
{
...
@@ -2444,7 +2432,7 @@ lock_rec_inherit_to_gap(
...
@@ -2444,7 +2432,7 @@ lock_rec_inherit_to_gap(
heir
,
lock
->
index
,
lock
->
trx
);
heir
,
lock
->
index
,
lock
->
trx
);
}
}
lock
=
lock_rec_get_next
(
rec
,
comp
,
lock
);
lock
=
lock_rec_get_next
(
rec
,
lock
);
}
}
}
}
...
@@ -2461,13 +2449,11 @@ lock_rec_inherit_to_gap_if_gap_lock(
...
@@ -2461,13 +2449,11 @@ lock_rec_inherit_to_gap_if_gap_lock(
the locks on this record */
the locks on this record */
{
{
lock_t
*
lock
;
lock_t
*
lock
;
ibool
comp
;
#ifdef UNIV_SYNC_DEBUG
#ifdef UNIV_SYNC_DEBUG
ut_ad
(
mutex_own
(
&
kernel_mutex
));
ut_ad
(
mutex_own
(
&
kernel_mutex
));
#endif
/* UNIV_SYNC_DEBUG */
#endif
/* UNIV_SYNC_DEBUG */
lock
=
lock_rec_get_first
(
rec
);
lock
=
lock_rec_get_first
(
rec
);
comp
=
page_is_comp
(
buf_frame_align
(
rec
));
while
(
lock
!=
NULL
)
{
while
(
lock
!=
NULL
)
{
if
(
!
lock_rec_get_insert_intention
(
lock
)
if
(
!
lock_rec_get_insert_intention
(
lock
)
...
@@ -2479,7 +2465,7 @@ lock_rec_inherit_to_gap_if_gap_lock(
...
@@ -2479,7 +2465,7 @@ lock_rec_inherit_to_gap_if_gap_lock(
heir
,
lock
->
index
,
lock
->
trx
);
heir
,
lock
->
index
,
lock
->
trx
);
}
}
lock
=
lock_rec_get_next
(
rec
,
comp
,
lock
);
lock
=
lock_rec_get_next
(
rec
,
lock
);
}
}
}
}
...
@@ -2493,7 +2479,7 @@ lock_rec_move(
...
@@ -2493,7 +2479,7 @@ lock_rec_move(
rec_t
*
receiver
,
/* in: record which gets locks; this record
rec_t
*
receiver
,
/* in: record which gets locks; this record
must have no lock requests on it! */
must have no lock requests on it! */
rec_t
*
donator
,
/* in: record which gives locks */
rec_t
*
donator
,
/* in: record which gives locks */
ibool
comp
)
/* in: TRUE
=compact page format */
ulint
comp
)
/* in: nonzero
=compact page format */
{
{
lock_t
*
lock
;
lock_t
*
lock
;
ulint
heap_no
;
ulint
heap_no
;
...
@@ -2523,7 +2509,7 @@ lock_rec_move(
...
@@ -2523,7 +2509,7 @@ lock_rec_move(
lock_rec_add_to_queue
(
type_mode
,
receiver
,
lock
->
index
,
lock_rec_add_to_queue
(
type_mode
,
receiver
,
lock
->
index
,
lock
->
trx
);
lock
->
trx
);
lock
=
lock_rec_get_next
(
donator
,
comp
,
lock
);
lock
=
lock_rec_get_next
(
donator
,
lock
);
}
}
ut_ad
(
lock_rec_get_first
(
donator
)
==
NULL
);
ut_ad
(
lock_rec_get_first
(
donator
)
==
NULL
);
...
@@ -2549,7 +2535,7 @@ lock_move_reorganize_page(
...
@@ -2549,7 +2535,7 @@ lock_move_reorganize_page(
UT_LIST_BASE_NODE_T
(
lock_t
)
old_locks
;
UT_LIST_BASE_NODE_T
(
lock_t
)
old_locks
;
mem_heap_t
*
heap
=
NULL
;
mem_heap_t
*
heap
=
NULL
;
rec_t
*
sup
;
rec_t
*
sup
;
ibool
comp
;
ulint
comp
;
lock_mutex_enter_kernel
();
lock_mutex_enter_kernel
();
...
@@ -2668,8 +2654,9 @@ lock_move_rec_list_end(
...
@@ -2668,8 +2654,9 @@ lock_move_rec_list_end(
ulint
heap_no
;
ulint
heap_no
;
rec_t
*
sup
;
rec_t
*
sup
;
ulint
type_mode
;
ulint
type_mode
;
ibool
comp
;
ulint
comp
;
ut_ad
(
page
==
buf_frame_align
(
rec
));
lock_mutex_enter_kernel
();
lock_mutex_enter_kernel
();
/* Note: when we move locks from record to record, waiting locks
/* Note: when we move locks from record to record, waiting locks
...
@@ -2754,7 +2741,7 @@ lock_move_rec_list_start(
...
@@ -2754,7 +2741,7 @@ lock_move_rec_list_start(
page_cur_t
cur2
;
page_cur_t
cur2
;
ulint
heap_no
;
ulint
heap_no
;
ulint
type_mode
;
ulint
type_mode
;
ibool
comp
;
ulint
comp
;
ut_a
(
new_page
);
ut_a
(
new_page
);
...
@@ -2763,6 +2750,7 @@ lock_move_rec_list_start(
...
@@ -2763,6 +2750,7 @@ lock_move_rec_list_start(
lock
=
lock_rec_get_first_on_page
(
page
);
lock
=
lock_rec_get_first_on_page
(
page
);
comp
=
page_is_comp
(
page
);
comp
=
page_is_comp
(
page
);
ut_ad
(
comp
==
page_is_comp
(
new_page
));
ut_ad
(
comp
==
page_is_comp
(
new_page
));
ut_ad
(
page
==
buf_frame_align
(
rec
));
while
(
lock
!=
NULL
)
{
while
(
lock
!=
NULL
)
{
...
@@ -2821,7 +2809,7 @@ lock_update_split_right(
...
@@ -2821,7 +2809,7 @@ lock_update_split_right(
page_t
*
right_page
,
/* in: right page */
page_t
*
right_page
,
/* in: right page */
page_t
*
left_page
)
/* in: left page */
page_t
*
left_page
)
/* in: left page */
{
{
ibool
comp
;
ulint
comp
;
lock_mutex_enter_kernel
();
lock_mutex_enter_kernel
();
comp
=
page_is_comp
(
left_page
);
comp
=
page_is_comp
(
left_page
);
ut_ad
(
comp
==
page_is_comp
(
right_page
));
ut_ad
(
comp
==
page_is_comp
(
right_page
));
...
@@ -2884,7 +2872,7 @@ lock_update_root_raise(
...
@@ -2884,7 +2872,7 @@ lock_update_root_raise(
page_t
*
new_page
,
/* in: index page to which copied */
page_t
*
new_page
,
/* in: index page to which copied */
page_t
*
root
)
/* in: root page */
page_t
*
root
)
/* in: root page */
{
{
ibool
comp
;
ulint
comp
;
lock_mutex_enter_kernel
();
lock_mutex_enter_kernel
();
comp
=
page_is_comp
(
root
);
comp
=
page_is_comp
(
root
);
ut_ad
(
comp
==
page_is_comp
(
new_page
));
ut_ad
(
comp
==
page_is_comp
(
new_page
));
...
@@ -2907,7 +2895,7 @@ lock_update_copy_and_discard(
...
@@ -2907,7 +2895,7 @@ lock_update_copy_and_discard(
page_t
*
new_page
,
/* in: index page to which copied */
page_t
*
new_page
,
/* in: index page to which copied */
page_t
*
page
)
/* in: index page; NOT the root! */
page_t
*
page
)
/* in: index page; NOT the root! */
{
{
ibool
comp
;
ulint
comp
;
lock_mutex_enter_kernel
();
lock_mutex_enter_kernel
();
comp
=
page_is_comp
(
page
);
comp
=
page_is_comp
(
page
);
ut_ad
(
comp
==
page_is_comp
(
new_page
));
ut_ad
(
comp
==
page_is_comp
(
new_page
));
...
@@ -2954,31 +2942,34 @@ lock_update_merge_left(
...
@@ -2954,31 +2942,34 @@ lock_update_merge_left(
page_t
*
right_page
)
/* in: merged index page which will be
page_t
*
right_page
)
/* in: merged index page which will be
discarded */
discarded */
{
{
ibool
comp
;
rec_t
*
left_next_rec
;
rec_t
*
left_supremum
;
ulint
comp
;
lock_mutex_enter_kernel
();
lock_mutex_enter_kernel
();
comp
=
page_is_comp
(
left_page
);
comp
=
page_is_comp
(
left_page
);
ut_ad
(
comp
==
page_is_comp
(
right_page
));
ut_ad
(
comp
==
page_is_comp
(
right_page
));
ut_ad
(
left_page
==
buf_frame_align
(
orig_pred
));
left_next_rec
=
page_rec_get_next
(
orig_pred
);
left_supremum
=
page_get_supremum_rec
(
left_page
);
if
(
page_rec_get_next
(
orig_pred
)
!=
page_get_supremum_rec
(
left_page
))
{
if
(
UNIV_LIKELY
(
left_next_rec
!=
left_supremum
))
{
/* Inherit the locks on the supremum of the left page to the
/* Inherit the locks on the supremum of the left page to the
first record which was moved from the right page */
first record which was moved from the right page */
lock_rec_inherit_to_gap
(
page_rec_get_next
(
orig_pred
),
lock_rec_inherit_to_gap
(
left_next_rec
,
left_supremum
);
page_get_supremum_rec
(
left_page
));
/* Reset the locks on the supremum of the left page,
/* Reset the locks on the supremum of the left page,
releasing waiting transactions */
releasing waiting transactions */
lock_rec_reset_and_release_wait
(
page_get_supremum_rec
(
lock_rec_reset_and_release_wait
(
left_supremum
);
left_page
));
}
}
/* Move the locks from the supremum of right page to the supremum
/* Move the locks from the supremum of right page to the supremum
of the left page */
of the left page */
lock_rec_move
(
page_get_supremum_rec
(
left_page
),
lock_rec_move
(
left_supremum
,
page_get_supremum_rec
(
right_page
),
comp
);
page_get_supremum_rec
(
right_page
),
comp
);
lock_rec_free_all_from_discard_page
(
right_page
);
lock_rec_free_all_from_discard_page
(
right_page
);
...
@@ -3037,7 +3028,7 @@ lock_update_discard(
...
@@ -3037,7 +3028,7 @@ lock_update_discard(
lock_rec_reset_and_release_wait
(
rec
);
lock_rec_reset_and_release_wait
(
rec
);
if
(
rec
==
page_get_supremum_rec
(
page
))
{
if
(
page_rec_is_supremum
(
rec
))
{
break
;
break
;
}
}
...
@@ -3100,19 +3091,16 @@ actual record is being moved. */
...
@@ -3100,19 +3091,16 @@ actual record is being moved. */
void
void
lock_rec_store_on_page_infimum
(
lock_rec_store_on_page_infimum
(
/*===========================*/
/*===========================*/
page_t
*
page
,
/* in: page containing the record */
rec_t
*
rec
)
/* in: record whose lock state is stored
rec_t
*
rec
)
/* in: record whose lock state is stored
on the infimum record of the same page; lock
on the infimum record of the same page; lock
bits are reset on the record */
bits are reset on the record */
{
{
page_t
*
page
;
ut_ad
(
page
==
buf_frame_align
(
rec
));
ibool
comp
;
page
=
buf_frame_align
(
rec
);
comp
=
page_is_comp
(
page
);
lock_mutex_enter_kernel
();
lock_mutex_enter_kernel
();
lock_rec_move
(
page_get_infimum_rec
(
page
),
rec
,
comp
);
lock_rec_move
(
page_get_infimum_rec
(
page
),
rec
,
page_is_comp
(
page
)
);
lock_mutex_exit_kernel
();
lock_mutex_exit_kernel
();
}
}
...
@@ -3129,10 +3117,10 @@ lock_rec_restore_from_page_infimum(
...
@@ -3129,10 +3117,10 @@ lock_rec_restore_from_page_infimum(
whose infimum stored the lock state; lock bits are
whose infimum stored the lock state; lock bits are
reset on the infimum */
reset on the infimum */
{
{
ibool
comp
;
ulint
comp
;
lock_mutex_enter_kernel
();
lock_mutex_enter_kernel
();
comp
=
page_is_comp
(
page
);
comp
=
page_is_comp
(
page
);
ut_ad
(
comp
==
page_is_comp
(
buf_frame_align
(
rec
)
));
ut_ad
(
!
comp
==
!
page_rec_is_comp
(
rec
));
lock_rec_move
(
rec
,
page_get_infimum_rec
(
page
),
comp
);
lock_rec_move
(
rec
,
page_get_infimum_rec
(
page
),
comp
);
...
@@ -4483,15 +4471,14 @@ lock_rec_queue_validate(
...
@@ -4483,15 +4471,14 @@ lock_rec_queue_validate(
{
{
trx_t
*
impl_trx
;
trx_t
*
impl_trx
;
lock_t
*
lock
;
lock_t
*
lock
;
ibool
comp
;
ut_a
(
rec
);
ut_a
(
rec
);
ut_ad
(
rec_offs_validate
(
rec
,
index
,
offsets
));
ut_ad
(
rec_offs_validate
(
rec
,
index
,
offsets
));
comp
=
page_is_comp
(
buf_frame_align
(
rec
));
ut_ad
(
!
page_rec_is_comp
(
rec
)
==
!
rec_offs_comp
(
offsets
));
lock_mutex_enter_kernel
();
lock_mutex_enter_kernel
();
if
(
page_rec_is_supremum
(
rec
)
||
page_rec_is_infimum
(
rec
))
{
if
(
!
page_rec_is_user_rec
(
rec
))
{
lock
=
lock_rec_get_first
(
rec
);
lock
=
lock_rec_get_first
(
rec
);
...
@@ -4511,7 +4498,7 @@ lock_rec_queue_validate(
...
@@ -4511,7 +4498,7 @@ lock_rec_queue_validate(
ut_a
(
lock
->
index
==
index
);
ut_a
(
lock
->
index
==
index
);
}
}
lock
=
lock_rec_get_next
(
rec
,
comp
,
lock
);
lock
=
lock_rec_get_next
(
rec
,
lock
);
}
}
lock_mutex_exit_kernel
();
lock_mutex_exit_kernel
();
...
@@ -4524,10 +4511,10 @@ lock_rec_queue_validate(
...
@@ -4524,10 +4511,10 @@ lock_rec_queue_validate(
impl_trx
=
lock_clust_rec_some_has_impl
(
rec
,
index
,
offsets
);
impl_trx
=
lock_clust_rec_some_has_impl
(
rec
,
index
,
offsets
);
if
(
impl_trx
&&
lock_rec_other_has_expl_req
(
LOCK_S
,
0
,
if
(
impl_trx
&&
lock_rec_other_has_expl_req
(
LOCK_S
,
0
,
LOCK_WAIT
,
rec
,
comp
,
impl_trx
))
{
LOCK_WAIT
,
rec
,
impl_trx
))
{
ut_a
(
lock_rec_has_expl
(
LOCK_X
|
LOCK_REC_NOT_GAP
,
rec
,
ut_a
(
lock_rec_has_expl
(
LOCK_X
|
LOCK_REC_NOT_GAP
,
rec
,
comp
,
impl_trx
));
impl_trx
));
}
}
}
}
...
@@ -4541,10 +4528,10 @@ lock_rec_queue_validate(
...
@@ -4541,10 +4528,10 @@ lock_rec_queue_validate(
rec
,
index
,
offsets
);
rec
,
index
,
offsets
);
if
(
impl_trx
&&
lock_rec_other_has_expl_req
(
LOCK_S
,
0
,
if
(
impl_trx
&&
lock_rec_other_has_expl_req
(
LOCK_S
,
0
,
LOCK_WAIT
,
rec
,
comp
,
impl_trx
))
{
LOCK_WAIT
,
rec
,
impl_trx
))
{
ut_a
(
lock_rec_has_expl
(
LOCK_X
|
LOCK_REC_NOT_GAP
,
ut_a
(
lock_rec_has_expl
(
LOCK_X
|
LOCK_REC_NOT_GAP
,
rec
,
comp
,
impl_trx
));
rec
,
impl_trx
));
}
}
}
}
...
@@ -4561,21 +4548,23 @@ lock_rec_queue_validate(
...
@@ -4561,21 +4548,23 @@ lock_rec_queue_validate(
}
}
if
(
!
lock_rec_get_gap
(
lock
)
&&
!
lock_get_wait
(
lock
))
{
if
(
!
lock_rec_get_gap
(
lock
)
&&
!
lock_get_wait
(
lock
))
{
ulint
mode
;
if
(
lock_get_mode
(
lock
)
==
LOCK_S
)
{
if
(
lock_get_mode
(
lock
)
==
LOCK_S
)
{
ut_a
(
!
lock_rec_other_has_expl_req
(
LOCK_X
,
mode
=
LOCK_X
;
0
,
0
,
rec
,
comp
,
lock
->
trx
));
}
else
{
}
else
{
ut_a
(
!
lock_rec_other_has_expl_req
(
LOCK_S
,
mode
=
LOCK_S
;
0
,
0
,
rec
,
comp
,
lock
->
trx
));
}
}
ut_a
(
!
lock_rec_other_has_expl_req
(
mode
,
0
,
0
,
rec
,
lock
->
trx
));
}
else
if
(
lock_get_wait
(
lock
)
&&
!
lock_rec_get_gap
(
lock
))
{
}
else
if
(
lock_get_wait
(
lock
)
&&
!
lock_rec_get_gap
(
lock
))
{
ut_a
(
lock_rec_has_to_wait_in_queue
(
lock
));
ut_a
(
lock_rec_has_to_wait_in_queue
(
lock
));
}
}
lock
=
lock_rec_get_next
(
rec
,
comp
,
lock
);
lock
=
lock_rec_get_next
(
rec
,
lock
);
}
}
lock_mutex_exit_kernel
();
lock_mutex_exit_kernel
();
...
@@ -4887,7 +4876,7 @@ lock_rec_convert_impl_to_expl(
...
@@ -4887,7 +4876,7 @@ lock_rec_convert_impl_to_expl(
#endif
/* UNIV_SYNC_DEBUG */
#endif
/* UNIV_SYNC_DEBUG */
ut_ad
(
page_rec_is_user_rec
(
rec
));
ut_ad
(
page_rec_is_user_rec
(
rec
));
ut_ad
(
rec_offs_validate
(
rec
,
index
,
offsets
));
ut_ad
(
rec_offs_validate
(
rec
,
index
,
offsets
));
ut_ad
(
page_is_comp
(
buf_frame_align
(
rec
))
==
index
->
table
->
comp
);
ut_ad
(
!
page_rec_is_comp
(
rec
)
==
!
rec_offs_comp
(
offsets
)
);
if
(
index
->
type
&
DICT_CLUSTERED
)
{
if
(
index
->
type
&
DICT_CLUSTERED
)
{
impl_trx
=
lock_clust_rec_some_has_impl
(
rec
,
index
,
offsets
);
impl_trx
=
lock_clust_rec_some_has_impl
(
rec
,
index
,
offsets
);
...
@@ -4901,7 +4890,7 @@ lock_rec_convert_impl_to_expl(
...
@@ -4901,7 +4890,7 @@ lock_rec_convert_impl_to_expl(
record, set one for it */
record, set one for it */
if
(
!
lock_rec_has_expl
(
LOCK_X
|
LOCK_REC_NOT_GAP
,
rec
,
if
(
!
lock_rec_has_expl
(
LOCK_X
|
LOCK_REC_NOT_GAP
,
rec
,
i
ndex
->
table
->
comp
,
i
mpl_trx
))
{
impl_trx
))
{
lock_rec_add_to_queue
(
LOCK_REC
|
LOCK_X
lock_rec_add_to_queue
(
LOCK_REC
|
LOCK_X
|
LOCK_REC_NOT_GAP
,
rec
,
index
,
|
LOCK_REC_NOT_GAP
,
rec
,
index
,
...
...
innobase/mtr/mtr0log.c
View file @
b3d6f517
...
@@ -15,6 +15,7 @@ Created 12/7/1995 Heikki Tuuri
...
@@ -15,6 +15,7 @@ Created 12/7/1995 Heikki Tuuri
#include "buf0buf.h"
#include "buf0buf.h"
#include "dict0boot.h"
#include "dict0boot.h"
#include "log0recv.h"
#include "log0recv.h"
#include "page0page.h"
/************************************************************
/************************************************************
Catenates n bytes to the mtr log. */
Catenates n bytes to the mtr log. */
...
@@ -405,7 +406,9 @@ mlog_open_and_write_index(
...
@@ -405,7 +406,9 @@ mlog_open_and_write_index(
const
byte
*
log_start
;
const
byte
*
log_start
;
const
byte
*
log_end
;
const
byte
*
log_end
;
if
(
!
index
->
table
->
comp
)
{
ut_ad
(
!!
page_rec_is_comp
(
rec
)
==
index
->
table
->
comp
);
if
(
!
page_rec_is_comp
(
rec
))
{
log_start
=
log_ptr
=
mlog_open
(
mtr
,
11
+
size
);
log_start
=
log_ptr
=
mlog_open
(
mtr
,
11
+
size
);
if
(
!
log_ptr
)
{
if
(
!
log_ptr
)
{
return
(
NULL
);
/* logging is disabled */
return
(
NULL
);
/* logging is disabled */
...
@@ -498,6 +501,8 @@ mlog_parse_index(
...
@@ -498,6 +501,8 @@ mlog_parse_index(
dict_table_t
*
table
;
dict_table_t
*
table
;
dict_index_t
*
ind
;
dict_index_t
*
ind
;
ut_ad
(
comp
==
FALSE
||
comp
==
TRUE
);
if
(
comp
)
{
if
(
comp
)
{
if
(
end_ptr
<
ptr
+
4
)
{
if
(
end_ptr
<
ptr
+
4
)
{
return
(
NULL
);
return
(
NULL
);
...
...
innobase/page/page0cur.c
View file @
b3d6f517
...
@@ -515,8 +515,12 @@ page_cur_insert_rec_write_log(
...
@@ -515,8 +515,12 @@ page_cur_insert_rec_write_log(
byte
*
log_ptr
;
byte
*
log_ptr
;
byte
*
log_end
;
byte
*
log_end
;
ulint
i
;
ulint
i
;
ulint
comp
;
ut_a
(
rec_size
<
UNIV_PAGE_SIZE
);
ut_a
(
rec_size
<
UNIV_PAGE_SIZE
);
ut_ad
(
buf_frame_align
(
insert_rec
)
==
buf_frame_align
(
cursor_rec
));
ut_ad
(
!
page_rec_is_comp
(
insert_rec
)
==
!
index
->
table
->
comp
);
comp
=
page_rec_is_comp
(
insert_rec
);
{
{
mem_heap_t
*
heap
=
NULL
;
mem_heap_t
*
heap
=
NULL
;
...
@@ -565,7 +569,7 @@ page_cur_insert_rec_write_log(
...
@@ -565,7 +569,7 @@ page_cur_insert_rec_write_log(
ins_ptr
++
;
ins_ptr
++
;
cur_ptr
++
;
cur_ptr
++
;
}
else
if
((
i
<
extra_size
)
}
else
if
((
i
<
extra_size
)
&&
(
i
>=
extra_size
-
(
index
->
table
->
comp
&&
(
i
>=
extra_size
-
(
comp
?
REC_N_NEW_EXTRA_BYTES
?
REC_N_NEW_EXTRA_BYTES
:
REC_N_OLD_EXTRA_BYTES
)))
{
:
REC_N_OLD_EXTRA_BYTES
)))
{
i
=
extra_size
;
i
=
extra_size
;
...
@@ -580,7 +584,7 @@ page_cur_insert_rec_write_log(
...
@@ -580,7 +584,7 @@ page_cur_insert_rec_write_log(
if
(
mtr_get_log_mode
(
mtr
)
!=
MTR_LOG_SHORT_INSERTS
)
{
if
(
mtr_get_log_mode
(
mtr
)
!=
MTR_LOG_SHORT_INSERTS
)
{
log_ptr
=
mlog_open_and_write_index
(
mtr
,
insert_rec
,
index
,
log_ptr
=
mlog_open_and_write_index
(
mtr
,
insert_rec
,
index
,
index
->
table
->
comp
comp
?
MLOG_COMP_REC_INSERT
:
MLOG_REC_INSERT
,
?
MLOG_COMP_REC_INSERT
:
MLOG_REC_INSERT
,
2
+
5
+
1
+
5
+
5
+
MLOG_BUF_MARGIN
);
2
+
5
+
1
+
5
+
5
+
MLOG_BUF_MARGIN
);
...
@@ -605,8 +609,8 @@ page_cur_insert_rec_write_log(
...
@@ -605,8 +609,8 @@ page_cur_insert_rec_write_log(
log_end
=
&
log_ptr
[
5
+
1
+
5
+
5
+
MLOG_BUF_MARGIN
];
log_end
=
&
log_ptr
[
5
+
1
+
5
+
5
+
MLOG_BUF_MARGIN
];
}
}
if
((
rec_get_info_and_status_bits
(
insert_rec
,
index
->
table
->
comp
)
!=
if
((
rec_get_info_and_status_bits
(
insert_rec
,
comp
)
!=
rec_get_info_and_status_bits
(
cursor_rec
,
index
->
table
->
comp
))
rec_get_info_and_status_bits
(
cursor_rec
,
comp
))
||
(
extra_size
!=
cur_extra_size
)
||
(
extra_size
!=
cur_extra_size
)
||
(
rec_size
!=
cur_rec_size
))
{
||
(
rec_size
!=
cur_rec_size
))
{
...
@@ -622,8 +626,7 @@ page_cur_insert_rec_write_log(
...
@@ -622,8 +626,7 @@ page_cur_insert_rec_write_log(
if
(
extra_info_yes
)
{
if
(
extra_info_yes
)
{
/* Write the info bits */
/* Write the info bits */
mach_write_to_1
(
log_ptr
,
mach_write_to_1
(
log_ptr
,
rec_get_info_and_status_bits
(
insert_rec
,
rec_get_info_and_status_bits
(
insert_rec
,
comp
));
index
->
table
->
comp
));
log_ptr
++
;
log_ptr
++
;
/* Write the record origin offset */
/* Write the record origin offset */
...
@@ -757,6 +760,8 @@ page_cur_parse_insert_rec(
...
@@ -757,6 +760,8 @@ page_cur_parse_insert_rec(
return
(
ptr
+
end_seg_len
);
return
(
ptr
+
end_seg_len
);
}
}
ut_ad
(
!!
page_is_comp
(
page
)
==
index
->
table
->
comp
);
/* Read from the log the inserted index record end segment which
/* Read from the log the inserted index record end segment which
differs from the cursor record */
differs from the cursor record */
...
@@ -771,7 +776,7 @@ page_cur_parse_insert_rec(
...
@@ -771,7 +776,7 @@ page_cur_parse_insert_rec(
if
(
extra_info_yes
==
0
)
{
if
(
extra_info_yes
==
0
)
{
info_and_status_bits
=
rec_get_info_and_status_bits
(
info_and_status_bits
=
rec_get_info_and_status_bits
(
cursor_rec
,
index
->
table
->
comp
);
cursor_rec
,
page_is_comp
(
page
)
);
origin_offset
=
rec_offs_extra_size
(
offsets
);
origin_offset
=
rec_offs_extra_size
(
offsets
);
mismatch_index
=
rec_offs_size
(
offsets
)
-
end_seg_len
;
mismatch_index
=
rec_offs_size
(
offsets
)
-
end_seg_len
;
}
}
...
@@ -807,7 +812,7 @@ page_cur_parse_insert_rec(
...
@@ -807,7 +812,7 @@ page_cur_parse_insert_rec(
ut_memcpy
(
buf
,
rec_get_start
(
cursor_rec
,
offsets
),
mismatch_index
);
ut_memcpy
(
buf
,
rec_get_start
(
cursor_rec
,
offsets
),
mismatch_index
);
ut_memcpy
(
buf
+
mismatch_index
,
ptr
,
end_seg_len
);
ut_memcpy
(
buf
+
mismatch_index
,
ptr
,
end_seg_len
);
rec_set_info_and_status_bits
(
buf
+
origin_offset
,
index
->
table
->
comp
,
rec_set_info_and_status_bits
(
buf
+
origin_offset
,
page_is_comp
(
page
)
,
info_and_status_bits
);
info_and_status_bits
);
page_cur_position
(
cursor_rec
,
&
cursor
);
page_cur_position
(
cursor_rec
,
&
cursor
);
...
@@ -861,7 +866,7 @@ page_cur_insert_rec_low(
...
@@ -861,7 +866,7 @@ page_cur_insert_rec_low(
rec_t
*
owner_rec
;
rec_t
*
owner_rec
;
ulint
n_owned
;
ulint
n_owned
;
mem_heap_t
*
heap
=
NULL
;
mem_heap_t
*
heap
=
NULL
;
ibool
comp
=
index
->
table
->
comp
;
ulint
comp
;
ut_ad
(
cursor
&&
mtr
);
ut_ad
(
cursor
&&
mtr
);
ut_ad
(
tuple
||
rec
);
ut_ad
(
tuple
||
rec
);
...
@@ -869,8 +874,8 @@ page_cur_insert_rec_low(
...
@@ -869,8 +874,8 @@ page_cur_insert_rec_low(
ut_ad
(
rec
||
dtuple_check_typed
(
tuple
));
ut_ad
(
rec
||
dtuple_check_typed
(
tuple
));
page
=
page_cur_get_page
(
cursor
);
page
=
page_cur_get_page
(
cursor
);
comp
=
page_is_comp
(
page
);
ut_ad
(
page_is_comp
(
page
)
==
comp
);
ut_ad
(
index
->
table
->
comp
==
!!
comp
);
ut_ad
(
cursor
->
rec
!=
page_get_supremum_rec
(
page
));
ut_ad
(
cursor
->
rec
!=
page_get_supremum_rec
(
page
));
...
@@ -1000,8 +1005,10 @@ page_copy_rec_list_to_created_page_write_log(
...
@@ -1000,8 +1005,10 @@ page_copy_rec_list_to_created_page_write_log(
{
{
byte
*
log_ptr
;
byte
*
log_ptr
;
ut_ad
(
!!
page_is_comp
(
page
)
==
index
->
table
->
comp
);
log_ptr
=
mlog_open_and_write_index
(
mtr
,
page
,
index
,
log_ptr
=
mlog_open_and_write_index
(
mtr
,
page
,
index
,
index
->
table
->
comp
page_is_comp
(
page
)
?
MLOG_COMP_LIST_END_COPY_CREATED
?
MLOG_COMP_LIST_END_COPY_CREATED
:
MLOG_LIST_END_COPY_CREATED
,
4
);
:
MLOG_LIST_END_COPY_CREATED
,
4
);
ut_a
(
log_ptr
);
ut_a
(
log_ptr
);
...
@@ -1084,7 +1091,7 @@ page_copy_rec_list_end_to_created_page(
...
@@ -1084,7 +1091,7 @@ page_copy_rec_list_end_to_created_page(
ulint
log_mode
;
ulint
log_mode
;
byte
*
log_ptr
;
byte
*
log_ptr
;
ulint
log_data_len
;
ulint
log_data_len
;
ibool
comp
=
page_is_comp
(
page
);
ulint
comp
=
page_is_comp
(
page
);
mem_heap_t
*
heap
=
NULL
;
mem_heap_t
*
heap
=
NULL
;
ulint
offsets_
[
REC_OFFS_NORMAL_SIZE
];
ulint
offsets_
[
REC_OFFS_NORMAL_SIZE
];
ulint
*
offsets
=
offsets_
;
ulint
*
offsets
=
offsets_
;
...
@@ -1230,8 +1237,10 @@ page_cur_delete_rec_write_log(
...
@@ -1230,8 +1237,10 @@ page_cur_delete_rec_write_log(
{
{
byte
*
log_ptr
;
byte
*
log_ptr
;
ut_ad
(
!!
page_rec_is_comp
(
rec
)
==
index
->
table
->
comp
);
log_ptr
=
mlog_open_and_write_index
(
mtr
,
rec
,
index
,
log_ptr
=
mlog_open_and_write_index
(
mtr
,
rec
,
index
,
index
->
table
->
comp
page_rec_is_comp
(
rec
)
?
MLOG_COMP_REC_DELETE
?
MLOG_COMP_REC_DELETE
:
MLOG_REC_DELETE
,
2
);
:
MLOG_REC_DELETE
,
2
);
...
@@ -1242,7 +1251,7 @@ page_cur_delete_rec_write_log(
...
@@ -1242,7 +1251,7 @@ page_cur_delete_rec_write_log(
}
}
/* Write the cursor rec offset as a 2-byte ulint */
/* Write the cursor rec offset as a 2-byte ulint */
mach_write_to_2
(
log_ptr
,
rec
-
buf_frame_align
(
rec
));
mach_write_to_2
(
log_ptr
,
ut_align_offset
(
rec
,
UNIV_PAGE_SIZE
));
mlog_close
(
mtr
,
log_ptr
+
2
);
mlog_close
(
mtr
,
log_ptr
+
2
);
}
}
...
@@ -1320,6 +1329,7 @@ page_cur_delete_rec(
...
@@ -1320,6 +1329,7 @@ page_cur_delete_rec(
page
=
page_cur_get_page
(
cursor
);
page
=
page_cur_get_page
(
cursor
);
current_rec
=
cursor
->
rec
;
current_rec
=
cursor
->
rec
;
ut_ad
(
rec_offs_validate
(
current_rec
,
index
,
offsets
));
ut_ad
(
rec_offs_validate
(
current_rec
,
index
,
offsets
));
ut_ad
(
!!
page_is_comp
(
page
)
==
index
->
table
->
comp
);
/* The record must not be the supremum or infimum record. */
/* The record must not be the supremum or infimum record. */
ut_ad
(
current_rec
!=
page_get_supremum_rec
(
page
));
ut_ad
(
current_rec
!=
page_get_supremum_rec
(
page
));
...
...
innobase/page/page0page.c
View file @
b3d6f517
...
@@ -72,65 +72,70 @@ page_dir_find_owner_slot(
...
@@ -72,65 +72,70 @@ page_dir_find_owner_slot(
/* out: the directory slot number */
/* out: the directory slot number */
rec_t
*
rec
)
/* in: the physical record */
rec_t
*
rec
)
/* in: the physical record */
{
{
ulint
i
;
page_t
*
page
;
ulint
steps
=
0
;
register
uint16
rec_offs_bytes
;
page_t
*
page
;
register
page_dir_slot_t
*
slot
;
page_dir_slot_t
*
slot
;
register
const
page_dir_slot_t
*
first_slot
;
rec_t
*
original_rec
=
rec
;
register
rec_t
*
r
=
rec
;
ibool
comp
;
ut_ad
(
page_rec_check
(
rec
));
ut_ad
(
page_rec_check
(
rec
));
page
=
buf_frame_align
(
rec
);
page
=
buf_frame_align
(
rec
);
comp
=
page_is_comp
(
page
);
first_slot
=
page_dir_get_nth_slot
(
page
,
0
);
slot
=
page_dir_get_nth_slot
(
page
,
page_dir_get_n_slots
(
page
)
-
1
);
while
(
rec_get_n_owned
(
rec
,
comp
)
==
0
)
{
steps
++
;
if
(
page_is_comp
(
page
))
{
rec
=
page_rec_get_next
(
rec
);
while
(
rec_get_n_owned
(
r
,
TRUE
)
==
0
)
{
r
=
page
+
rec_get_next_offs
(
r
,
TRUE
);
ut_ad
(
r
>=
page
+
PAGE_NEW_SUPREMUM
);
ut_ad
(
r
<
page
+
(
UNIV_PAGE_SIZE
-
PAGE_DIR
));
}
}
else
{
while
(
rec_get_n_owned
(
r
,
FALSE
)
==
0
)
{
r
=
page
+
rec_get_next_offs
(
r
,
FALSE
);
ut_ad
(
r
>=
page
+
PAGE_OLD_SUPREMUM
);
ut_ad
(
r
<
page
+
(
UNIV_PAGE_SIZE
-
PAGE_DIR
));
}
}
}
page
=
buf_frame_align
(
rec
);
i
=
page_dir_get_n_slots
(
page
)
-
1
;
rec_offs_bytes
=
mach_encode_2
(
r
-
page
);
slot
=
page_dir_get_nth_slot
(
page
,
i
);
while
(
page_dir_slot_get_rec
(
slot
)
!=
rec
)
{
while
(
UNIV_LIKELY
(
*
(
uint16
*
)
slot
!=
rec_offs_bytes
)
)
{
if
(
i
==
0
)
{
if
(
UNIV_UNLIKELY
(
slot
==
first_slot
)
)
{
fprintf
(
stderr
,
fprintf
(
stderr
,
"InnoDB: Probable data corruption on page %lu
\n
"
"InnoDB: Probable data corruption on page %lu
\n
"
"InnoDB: Original record "
,
"InnoDB: Original record "
,
(
ulong
)
buf_frame_get_page_no
(
page
));
(
ulong
)
buf_frame_get_page_no
(
page
));
if
(
comp
)
{
if
(
page_is_comp
(
page
)
)
{
fputs
(
"(compact record)"
,
stderr
);
fputs
(
"(compact record)"
,
stderr
);
}
else
{
}
else
{
rec_print_old
(
stderr
,
original_
rec
);
rec_print_old
(
stderr
,
rec
);
}
}
fprintf
(
stderr
,
"
\n
"
fputs
(
"
\n
"
"InnoDB: on that page. Steps %lu.
\n
"
,
(
ulong
)
steps
);
"InnoDB: on that page.
\n
"
fputs
(
"InnoDB: Cannot find the dir slot for record "
,
"InnoDB: Cannot find the dir slot for record "
,
stderr
);
stderr
);
if
(
comp
)
{
if
(
page_is_comp
(
page
)
)
{
fputs
(
"(compact record)"
,
stderr
);
fputs
(
"(compact record)"
,
stderr
);
}
else
{
}
else
{
rec_print_old
(
stderr
,
rec
);
rec_print_old
(
stderr
,
page
+
mach_decode_2
(
rec_offs_bytes
));
}
}
fputs
(
"
\n
"
fputs
(
"
\n
"
"InnoDB: on that page!
\n
"
,
stderr
);
"InnoDB: on that page!
\n
"
,
stderr
);
buf_page_print
(
page
);
buf_page_print
(
page
);
ut_error
;
ut_error
;
}
}
i
--
;
slot
+=
PAGE_DIR_SLOT_SIZE
;
slot
=
page_dir_get_nth_slot
(
page
,
i
);
}
}
return
(
i
);
return
(
((
ulint
)
(
first_slot
-
slot
))
/
PAGE_DIR_SLOT_SIZE
);
}
}
/******************************************************************
/******************************************************************
...
@@ -290,7 +295,7 @@ page_create_write_log(
...
@@ -290,7 +295,7 @@ page_create_write_log(
buf_frame_t
*
frame
,
/* in: a buffer frame where the page is
buf_frame_t
*
frame
,
/* in: a buffer frame where the page is
created */
created */
mtr_t
*
mtr
,
/* in: mini-transaction handle */
mtr_t
*
mtr
,
/* in: mini-transaction handle */
ibool
comp
)
/* in: TRUE
=compact page format */
ulint
comp
)
/* in: nonzero
=compact page format */
{
{
mlog_write_initial_log_record
(
frame
,
mlog_write_initial_log_record
(
frame
,
comp
?
MLOG_COMP_PAGE_CREATE
:
MLOG_PAGE_CREATE
,
mtr
);
comp
?
MLOG_COMP_PAGE_CREATE
:
MLOG_PAGE_CREATE
,
mtr
);
...
@@ -305,7 +310,7 @@ page_parse_create(
...
@@ -305,7 +310,7 @@ page_parse_create(
/* out: end of log record or NULL */
/* out: end of log record or NULL */
byte
*
ptr
,
/* in: buffer */
byte
*
ptr
,
/* in: buffer */
byte
*
end_ptr
__attribute__
((
unused
)),
/* in: buffer end */
byte
*
end_ptr
__attribute__
((
unused
)),
/* in: buffer end */
ibool
comp
,
/* in: TRUE
=compact page format */
ulint
comp
,
/* in: nonzero
=compact page format */
page_t
*
page
,
/* in: page or NULL */
page_t
*
page
,
/* in: page or NULL */
mtr_t
*
mtr
)
/* in: mtr or NULL */
mtr_t
*
mtr
)
/* in: mtr or NULL */
{
{
...
@@ -330,7 +335,7 @@ page_create(
...
@@ -330,7 +335,7 @@ page_create(
buf_frame_t
*
frame
,
/* in: a buffer frame where the page is
buf_frame_t
*
frame
,
/* in: a buffer frame where the page is
created */
created */
mtr_t
*
mtr
,
/* in: mini-transaction handle */
mtr_t
*
mtr
,
/* in: mini-transaction handle */
ibool
comp
)
/* in: TRUE
=compact page format */
ulint
comp
)
/* in: nonzero
=compact page format */
{
{
page_dir_slot_t
*
slot
;
page_dir_slot_t
*
slot
;
mem_heap_t
*
heap
;
mem_heap_t
*
heap
;
...
@@ -396,9 +401,9 @@ page_create(
...
@@ -396,9 +401,9 @@ page_create(
dtuple_set_info_bits
(
tuple
,
REC_STATUS_SUPREMUM
);
dtuple_set_info_bits
(
tuple
,
REC_STATUS_SUPREMUM
);
field
=
dtuple_get_nth_field
(
tuple
,
0
);
field
=
dtuple_get_nth_field
(
tuple
,
0
);
dfield_set_data
(
field
,
"supremum"
,
9
-
comp
);
dfield_set_data
(
field
,
"supremum"
,
comp
?
8
:
9
);
dtype_set
(
dfield_get_type
(
field
),
dtype_set
(
dfield_get_type
(
field
),
DATA_VARCHAR
,
DATA_ENGLISH
|
DATA_NOT_NULL
,
9
-
comp
,
0
);
DATA_VARCHAR
,
DATA_ENGLISH
|
DATA_NOT_NULL
,
comp
?
8
:
9
,
0
);
supremum_rec
=
rec_convert_dtuple_to_rec
(
heap_top
,
index
,
tuple
);
supremum_rec
=
rec_convert_dtuple_to_rec
(
heap_top
,
index
,
tuple
);
...
@@ -478,10 +483,11 @@ page_copy_rec_list_end_no_locks(
...
@@ -478,10 +483,11 @@ page_copy_rec_list_end_no_locks(
page_cur_move_to_next
(
&
cur1
);
page_cur_move_to_next
(
&
cur1
);
}
}
ut_a
(
index
->
table
->
comp
==
page_is_comp
(
page
)
);
ut_a
(
!!
page_is_comp
(
new_page
)
==
index
->
table
->
comp
);
ut_a
(
index
->
table
->
comp
==
page_is_comp
(
new_
page
));
ut_a
(
page_is_comp
(
new_page
)
==
page_is_comp
(
page
));
ut_a
(
mach_read_from_2
(
new_page
+
UNIV_PAGE_SIZE
-
10
)
==
(
ulint
)
ut_a
(
mach_read_from_2
(
new_page
+
UNIV_PAGE_SIZE
-
10
)
==
(
ulint
)
(
index
->
table
->
comp
?
PAGE_NEW_INFIMUM
:
PAGE_OLD_INFIMUM
));
(
page_is_comp
(
new_page
)
?
PAGE_NEW_INFIMUM
:
PAGE_OLD_INFIMUM
));
page_cur_set_before_first
(
new_page
,
&
cur2
);
page_cur_set_before_first
(
new_page
,
&
cur2
);
...
@@ -489,12 +495,15 @@ page_copy_rec_list_end_no_locks(
...
@@ -489,12 +495,15 @@ page_copy_rec_list_end_no_locks(
sup
=
page_get_supremum_rec
(
page
);
sup
=
page_get_supremum_rec
(
page
);
while
(
sup
!=
page_cur_get_rec
(
&
cur1
)
)
{
for
(;;
)
{
rec_t
*
cur1_rec
=
page_cur_get_rec
(
&
cur1
);
rec_t
*
cur1_rec
=
page_cur_get_rec
(
&
cur1
);
if
(
cur1_rec
==
sup
)
{
break
;
}
offsets
=
rec_get_offsets
(
cur1_rec
,
index
,
offsets
,
offsets
=
rec_get_offsets
(
cur1_rec
,
index
,
offsets
,
ULINT_UNDEFINED
,
&
heap
);
ULINT_UNDEFINED
,
&
heap
);
if
(
!
page_cur_rec_insert
(
&
cur2
,
cur1_rec
,
index
,
if
(
UNIV_UNLIKELY
(
!
page_cur_rec_insert
(
&
cur2
,
cur1_rec
,
index
,
offsets
,
mtr
))
{
offsets
,
mtr
))
)
{
/* Track an assertion failure reported on the mailing
/* Track an assertion failure reported on the mailing
list on June 18th, 2003 */
list on June 18th, 2003 */
...
@@ -619,7 +628,6 @@ UNIV_INLINE
...
@@ -619,7 +628,6 @@ UNIV_INLINE
void
void
page_delete_rec_list_write_log
(
page_delete_rec_list_write_log
(
/*===========================*/
/*===========================*/
page_t
*
page
,
/* in: index page */
rec_t
*
rec
,
/* in: record on page */
rec_t
*
rec
,
/* in: record on page */
dict_index_t
*
index
,
/* in: record descriptor */
dict_index_t
*
index
,
/* in: record descriptor */
byte
type
,
/* in: operation type:
byte
type
,
/* in: operation type:
...
@@ -632,10 +640,10 @@ page_delete_rec_list_write_log(
...
@@ -632,10 +640,10 @@ page_delete_rec_list_write_log(
||
type
==
MLOG_COMP_LIST_END_DELETE
||
type
==
MLOG_COMP_LIST_END_DELETE
||
type
==
MLOG_COMP_LIST_START_DELETE
);
||
type
==
MLOG_COMP_LIST_START_DELETE
);
log_ptr
=
mlog_open_and_write_index
(
mtr
,
page
,
index
,
type
,
2
);
log_ptr
=
mlog_open_and_write_index
(
mtr
,
rec
,
index
,
type
,
2
);
if
(
log_ptr
)
{
if
(
log_ptr
)
{
/* Write the parameter as a 2-byte ulint */
/* Write the parameter as a 2-byte ulint */
mach_write_to_2
(
log_ptr
,
rec
-
page
);
mach_write_to_2
(
log_ptr
,
ut_align_offset
(
rec
,
UNIV_PAGE_SIZE
)
);
mlog_close
(
mtr
,
log_ptr
+
2
);
mlog_close
(
mtr
,
log_ptr
+
2
);
}
}
}
}
...
@@ -679,6 +687,8 @@ page_parse_delete_rec_list(
...
@@ -679,6 +687,8 @@ page_parse_delete_rec_list(
return
(
ptr
);
return
(
ptr
);
}
}
ut_ad
(
!!
page_is_comp
(
page
)
==
index
->
table
->
comp
);
if
(
type
==
MLOG_LIST_END_DELETE
if
(
type
==
MLOG_LIST_END_DELETE
||
type
==
MLOG_COMP_LIST_END_DELETE
)
{
||
type
==
MLOG_COMP_LIST_END_DELETE
)
{
page_delete_rec_list_end
(
page
,
page
+
offset
,
index
,
page_delete_rec_list_end
(
page
,
page
+
offset
,
index
,
...
@@ -716,7 +726,7 @@ page_delete_rec_list_end(
...
@@ -716,7 +726,7 @@ page_delete_rec_list_end(
ulint
count
;
ulint
count
;
ulint
n_owned
;
ulint
n_owned
;
rec_t
*
sup
;
rec_t
*
sup
;
ibool
comp
;
ulint
comp
;
/* Reset the last insert info in the page header and increment
/* Reset the last insert info in the page header and increment
the modify clock for the frame */
the modify clock for the frame */
...
@@ -731,12 +741,12 @@ page_delete_rec_list_end(
...
@@ -731,12 +741,12 @@ page_delete_rec_list_end(
sup
=
page_get_supremum_rec
(
page
);
sup
=
page_get_supremum_rec
(
page
);
if
(
rec
==
page_get_infimum_rec
(
page
))
{
comp
=
page_is_comp
(
page
);
if
(
page_rec_is_infimum_low
(
rec
-
page
))
{
rec
=
page_rec_get_next
(
rec
);
rec
=
page_rec_get_next
(
rec
);
}
}
comp
=
page_is_comp
(
page
);
page_delete_rec_list_write_log
(
rec
,
index
,
page_delete_rec_list_write_log
(
page
,
rec
,
index
,
comp
?
MLOG_COMP_LIST_END_DELETE
:
MLOG_LIST_END_DELETE
,
mtr
);
comp
?
MLOG_COMP_LIST_END_DELETE
:
MLOG_LIST_END_DELETE
,
mtr
);
if
(
rec
==
sup
)
{
if
(
rec
==
sup
)
{
...
@@ -841,13 +851,15 @@ page_delete_rec_list_start(
...
@@ -841,13 +851,15 @@ page_delete_rec_list_start(
byte
type
;
byte
type
;
*
offsets_
=
(
sizeof
offsets_
)
/
sizeof
*
offsets_
;
*
offsets_
=
(
sizeof
offsets_
)
/
sizeof
*
offsets_
;
if
(
index
->
table
->
comp
)
{
ut_ad
(
!!
page_is_comp
(
page
)
==
index
->
table
->
comp
);
if
(
page_is_comp
(
page
))
{
type
=
MLOG_COMP_LIST_START_DELETE
;
type
=
MLOG_COMP_LIST_START_DELETE
;
}
else
{
}
else
{
type
=
MLOG_LIST_START_DELETE
;
type
=
MLOG_LIST_START_DELETE
;
}
}
page_delete_rec_list_write_log
(
page
,
rec
,
index
,
type
,
mtr
);
page_delete_rec_list_write_log
(
rec
,
index
,
type
,
mtr
);
page_cur_set_before_first
(
page
,
&
cur1
);
page_cur_set_before_first
(
page
,
&
cur1
);
...
@@ -1221,7 +1233,7 @@ page_rec_get_n_recs_before(
...
@@ -1221,7 +1233,7 @@ page_rec_get_n_recs_before(
rec_t
*
slot_rec
;
rec_t
*
slot_rec
;
page_t
*
page
;
page_t
*
page
;
ulint
i
;
ulint
i
;
ibool
comp
;
ulint
comp
;
lint
n
=
0
;
lint
n
=
0
;
ut_ad
(
page_rec_check
(
rec
));
ut_ad
(
page_rec_check
(
rec
));
...
@@ -1264,9 +1276,9 @@ page_rec_print(
...
@@ -1264,9 +1276,9 @@ page_rec_print(
rec_t
*
rec
,
/* in: physical record */
rec_t
*
rec
,
/* in: physical record */
const
ulint
*
offsets
)
/* in: record descriptor */
const
ulint
*
offsets
)
/* in: record descriptor */
{
{
ibool
comp
=
page_is_comp
(
buf_frame_align
(
rec
));
ulint
comp
=
page_is_comp
(
buf_frame_align
(
rec
));
ut_a
(
comp
==
rec_offs_comp
(
offsets
));
ut_a
(
!
comp
==
!
rec_offs_comp
(
offsets
));
rec_print_new
(
stderr
,
rec
,
offsets
);
rec_print_new
(
stderr
,
rec
,
offsets
);
fprintf
(
stderr
,
fprintf
(
stderr
,
" n_owned: %lu; heap_no: %lu; next rec: %lu
\n
"
,
" n_owned: %lu; heap_no: %lu; next rec: %lu
\n
"
,
...
@@ -1335,7 +1347,7 @@ page_print_list(
...
@@ -1335,7 +1347,7 @@ page_print_list(
ulint
*
offsets
=
offsets_
;
ulint
*
offsets
=
offsets_
;
*
offsets_
=
(
sizeof
offsets_
)
/
sizeof
*
offsets_
;
*
offsets_
=
(
sizeof
offsets_
)
/
sizeof
*
offsets_
;
ut_a
(
page_is_comp
(
page
)
==
index
->
table
->
comp
);
ut_a
(
!!
page_is_comp
(
page
)
==
index
->
table
->
comp
);
fprintf
(
stderr
,
fprintf
(
stderr
,
"--------------------------------
\n
"
"--------------------------------
\n
"
...
@@ -1447,11 +1459,11 @@ page_rec_validate(
...
@@ -1447,11 +1459,11 @@ page_rec_validate(
ulint
n_owned
;
ulint
n_owned
;
ulint
heap_no
;
ulint
heap_no
;
page_t
*
page
;
page_t
*
page
;
ibool
comp
;
ulint
comp
;
page
=
buf_frame_align
(
rec
);
page
=
buf_frame_align
(
rec
);
comp
=
page_is_comp
(
page
);
comp
=
page_is_comp
(
page
);
ut_a
(
comp
==
rec_offs_comp
(
offsets
));
ut_a
(
!
comp
==
!
rec_offs_comp
(
offsets
));
page_rec_check
(
rec
);
page_rec_check
(
rec
);
rec_validate
(
rec
,
offsets
);
rec_validate
(
rec
,
offsets
);
...
@@ -1528,7 +1540,7 @@ page_simple_validate(
...
@@ -1528,7 +1540,7 @@ page_simple_validate(
ulint
count
;
ulint
count
;
ulint
own_count
;
ulint
own_count
;
ibool
ret
=
FALSE
;
ibool
ret
=
FALSE
;
ibool
comp
=
page_is_comp
(
page
);
ulint
comp
=
page_is_comp
(
page
);
/* Check first that the record heap and the directory do not
/* Check first that the record heap and the directory do not
overlap. */
overlap. */
...
@@ -1725,11 +1737,11 @@ page_validate(
...
@@ -1725,11 +1737,11 @@ page_validate(
ulint
n_slots
;
ulint
n_slots
;
ibool
ret
=
FALSE
;
ibool
ret
=
FALSE
;
ulint
i
;
ulint
i
;
ibool
comp
=
page_is_comp
(
page
);
ulint
comp
=
page_is_comp
(
page
);
ulint
*
offsets
=
NULL
;
ulint
*
offsets
=
NULL
;
ulint
*
old_offsets
=
NULL
;
ulint
*
old_offsets
=
NULL
;
if
(
comp
!=
index
->
table
->
comp
)
{
if
(
!!
comp
!=
index
->
table
->
comp
)
{
fputs
(
"InnoDB: 'compact format' flag mismatch
\n
"
,
stderr
);
fputs
(
"InnoDB: 'compact format' flag mismatch
\n
"
,
stderr
);
goto
func_exit2
;
goto
func_exit2
;
}
}
...
@@ -1810,8 +1822,7 @@ page_validate(
...
@@ -1810,8 +1822,7 @@ page_validate(
}
}
}
}
if
((
rec
!=
page_get_supremum_rec
(
page
))
if
(
page_rec_is_user_rec
(
rec
))
{
&&
(
rec
!=
page_get_infimum_rec
(
page
)))
{
data_size
+=
rec_offs_size
(
offsets
);
data_size
+=
rec_offs_size
(
offsets
);
}
}
...
...
innobase/rem/rem0cmp.c
View file @
b3d6f517
...
@@ -727,7 +727,7 @@ cmp_rec_rec_with_match(
...
@@ -727,7 +727,7 @@ cmp_rec_rec_with_match(
ulint
cur_bytes
;
/* number of already matched bytes in current
ulint
cur_bytes
;
/* number of already matched bytes in current
field */
field */
int
ret
=
3333
;
/* return value */
int
ret
=
3333
;
/* return value */
ibool
comp
;
ulint
comp
;
ut_ad
(
rec1
&&
rec2
&&
index
);
ut_ad
(
rec1
&&
rec2
&&
index
);
ut_ad
(
rec_offs_validate
(
rec1
,
index
,
offsets1
));
ut_ad
(
rec_offs_validate
(
rec1
,
index
,
offsets1
));
...
...
innobase/row/row0ins.c
View file @
b3d6f517
...
@@ -1255,9 +1255,11 @@ row_ins_check_foreign_constraint(
...
@@ -1255,9 +1255,11 @@ row_ins_check_foreign_constraint(
/* Scan index records and check if there is a matching record */
/* Scan index records and check if there is a matching record */
for
(;;)
{
for
(;;)
{
page_t
*
page
;
rec
=
btr_pcur_get_rec
(
&
pcur
);
rec
=
btr_pcur_get_rec
(
&
pcur
);
page
=
buf_frame_align
(
rec
);
if
(
rec
==
page_get_infimum_rec
(
buf_frame_align
(
rec
)
))
{
if
(
rec
==
page_get_infimum_rec
(
page
))
{
goto
next_rec
;
goto
next_rec
;
}
}
...
@@ -1265,7 +1267,7 @@ row_ins_check_foreign_constraint(
...
@@ -1265,7 +1267,7 @@ row_ins_check_foreign_constraint(
offsets
=
rec_get_offsets
(
rec
,
check_index
,
offsets
=
rec_get_offsets
(
rec
,
check_index
,
offsets
,
ULINT_UNDEFINED
,
&
heap
);
offsets
,
ULINT_UNDEFINED
,
&
heap
);
if
(
rec
==
page_get_supremum_rec
(
buf_frame_align
(
rec
)
))
{
if
(
rec
==
page_get_supremum_rec
(
page
))
{
err
=
row_ins_set_shared_rec_lock
(
LOCK_ORDINARY
,
rec
,
err
=
row_ins_set_shared_rec_lock
(
LOCK_ORDINARY
,
rec
,
check_index
,
offsets
,
thr
);
check_index
,
offsets
,
thr
);
...
@@ -1529,12 +1531,7 @@ row_ins_dupl_error_with_rec(
...
@@ -1529,12 +1531,7 @@ row_ins_dupl_error_with_rec(
}
}
}
}
if
(
!
rec_get_deleted_flag
(
rec
,
index
->
table
->
comp
))
{
return
(
!
rec_get_deleted_flag
(
rec
,
rec_offs_comp
(
offsets
)));
return
(
TRUE
);
}
return
(
FALSE
);
}
}
/*******************************************************************
/*******************************************************************
...
@@ -1629,7 +1626,7 @@ row_ins_scan_sec_index_for_duplicate(
...
@@ -1629,7 +1626,7 @@ row_ins_scan_sec_index_for_duplicate(
break
;
break
;
}
}
if
(
rec
==
page_get_supremum_rec
(
buf_frame_align
(
rec
)
))
{
if
(
page_rec_is_supremum
(
rec
))
{
goto
next_rec
;
goto
next_rec
;
}
}
...
@@ -1697,7 +1694,6 @@ row_ins_duplicate_error_in_clust(
...
@@ -1697,7 +1694,6 @@ row_ins_duplicate_error_in_clust(
#ifndef UNIV_HOTBACKUP
#ifndef UNIV_HOTBACKUP
ulint
err
;
ulint
err
;
rec_t
*
rec
;
rec_t
*
rec
;
page_t
*
page
;
ulint
n_unique
;
ulint
n_unique
;
trx_t
*
trx
=
thr_get_trx
(
thr
);
trx_t
*
trx
=
thr_get_trx
(
thr
);
mem_heap_t
*
heap
=
NULL
;
mem_heap_t
*
heap
=
NULL
;
...
@@ -1728,9 +1724,8 @@ row_ins_duplicate_error_in_clust(
...
@@ -1728,9 +1724,8 @@ row_ins_duplicate_error_in_clust(
if
(
cursor
->
low_match
>=
n_unique
)
{
if
(
cursor
->
low_match
>=
n_unique
)
{
rec
=
btr_cur_get_rec
(
cursor
);
rec
=
btr_cur_get_rec
(
cursor
);
page
=
buf_frame_align
(
rec
);
if
(
rec
!=
page_get_infimum_rec
(
page
))
{
if
(
!
page_rec_is_infimum
(
rec
))
{
offsets
=
rec_get_offsets
(
rec
,
cursor
->
index
,
offsets
,
offsets
=
rec_get_offsets
(
rec
,
cursor
->
index
,
offsets
,
ULINT_UNDEFINED
,
&
heap
);
ULINT_UNDEFINED
,
&
heap
);
...
@@ -1772,9 +1767,8 @@ row_ins_duplicate_error_in_clust(
...
@@ -1772,9 +1767,8 @@ row_ins_duplicate_error_in_clust(
if
(
cursor
->
up_match
>=
n_unique
)
{
if
(
cursor
->
up_match
>=
n_unique
)
{
rec
=
page_rec_get_next
(
btr_cur_get_rec
(
cursor
));
rec
=
page_rec_get_next
(
btr_cur_get_rec
(
cursor
));
page
=
buf_frame_align
(
rec
);
if
(
rec
!=
page_get_supremum_rec
(
page
))
{
if
(
!
page_rec_is_supremum
(
rec
))
{
offsets
=
rec_get_offsets
(
rec
,
cursor
->
index
,
offsets
,
offsets
=
rec_get_offsets
(
rec
,
cursor
->
index
,
offsets
,
ULINT_UNDEFINED
,
&
heap
);
ULINT_UNDEFINED
,
&
heap
);
...
@@ -1842,7 +1836,6 @@ row_ins_must_modify(
...
@@ -1842,7 +1836,6 @@ row_ins_must_modify(
{
{
ulint
enough_match
;
ulint
enough_match
;
rec_t
*
rec
;
rec_t
*
rec
;
page_t
*
page
;
/* NOTE: (compare to the note in row_ins_duplicate_error) Because node
/* NOTE: (compare to the note in row_ins_duplicate_error) Because node
pointers on upper levels of the B-tree may match more to entry than
pointers on upper levels of the B-tree may match more to entry than
...
@@ -1856,9 +1849,8 @@ row_ins_must_modify(
...
@@ -1856,9 +1849,8 @@ row_ins_must_modify(
if
(
cursor
->
low_match
>=
enough_match
)
{
if
(
cursor
->
low_match
>=
enough_match
)
{
rec
=
btr_cur_get_rec
(
cursor
);
rec
=
btr_cur_get_rec
(
cursor
);
page
=
buf_frame_align
(
rec
);
if
(
rec
!=
page_get_infimum_rec
(
page
))
{
if
(
!
page_rec_is_infimum
(
rec
))
{
return
(
ROW_INS_PREV
);
return
(
ROW_INS_PREV
);
}
}
...
@@ -1897,7 +1889,6 @@ row_ins_index_entry_low(
...
@@ -1897,7 +1889,6 @@ row_ins_index_entry_low(
ulint
modify
=
0
;
/* remove warning */
ulint
modify
=
0
;
/* remove warning */
rec_t
*
insert_rec
;
rec_t
*
insert_rec
;
rec_t
*
rec
;
rec_t
*
rec
;
rec_t
*
first_rec
;
ulint
err
;
ulint
err
;
ulint
n_unique
;
ulint
n_unique
;
big_rec_t
*
big_rec
=
NULL
;
big_rec_t
*
big_rec
=
NULL
;
...
@@ -1932,15 +1923,20 @@ row_ins_index_entry_low(
...
@@ -1932,15 +1923,20 @@ row_ins_index_entry_low(
err
=
DB_SUCCESS
;
err
=
DB_SUCCESS
;
goto
function_exit
;
goto
function_exit
;
}
}
first_rec
=
page_rec_get_next
(
page_get_infimum_rec
(
buf_frame_align
(
btr_cur_get_rec
(
&
cursor
))));
if
(
!
page_rec_is_supremum
(
first_rec
))
{
#ifdef UNIV_DEBUG
ut_a
(
rec_get_n_fields
(
first_rec
,
index
)
{
page_t
*
page
=
btr_cur_get_page
(
&
cursor
);
rec_t
*
first_rec
=
page_rec_get_next
(
page_get_infimum_rec
(
page
));
if
(
UNIV_LIKELY
(
first_rec
!=
page_get_supremum_rec
(
page
)))
{
ut_a
(
rec_get_n_fields
(
first_rec
,
index
)
==
dtuple_get_n_fields
(
entry
));
==
dtuple_get_n_fields
(
entry
));
}
}
}
#endif
n_unique
=
dict_index_get_n_unique
(
index
);
n_unique
=
dict_index_get_n_unique
(
index
);
...
...
innobase/row/row0mysql.c
View file @
b3d6f517
...
@@ -265,7 +265,7 @@ row_mysql_store_col_in_innobase_format(
...
@@ -265,7 +265,7 @@ row_mysql_store_col_in_innobase_format(
necessarily the length of the actual
necessarily the length of the actual
payload data; if the column is a true
payload data; if the column is a true
VARCHAR then this is irrelevant */
VARCHAR then this is irrelevant */
ibool
comp
)
/* in: TRUE =
compact format */
ulint
comp
)
/* in: nonzero=
compact format */
{
{
byte
*
ptr
=
mysql_data
;
byte
*
ptr
=
mysql_data
;
dtype_t
*
dtype
;
dtype_t
*
dtype
;
...
...
innobase/row/row0row.c
View file @
b3d6f517
...
@@ -616,7 +616,6 @@ row_search_on_row_ref(
...
@@ -616,7 +616,6 @@ row_search_on_row_ref(
ulint
low_match
;
ulint
low_match
;
rec_t
*
rec
;
rec_t
*
rec
;
dict_index_t
*
index
;
dict_index_t
*
index
;
page_t
*
page
;
ut_ad
(
dtuple_check_typed
(
ref
));
ut_ad
(
dtuple_check_typed
(
ref
));
...
@@ -629,9 +628,8 @@ row_search_on_row_ref(
...
@@ -629,9 +628,8 @@ row_search_on_row_ref(
low_match
=
btr_pcur_get_low_match
(
pcur
);
low_match
=
btr_pcur_get_low_match
(
pcur
);
rec
=
btr_pcur_get_rec
(
pcur
);
rec
=
btr_pcur_get_rec
(
pcur
);
page
=
buf_frame_align
(
rec
);
if
(
rec
==
page_get_infimum_rec
(
page
))
{
if
(
page_rec_is_infimum
(
rec
))
{
return
(
FALSE
);
return
(
FALSE
);
}
}
...
@@ -702,7 +700,6 @@ row_search_index_entry(
...
@@ -702,7 +700,6 @@ row_search_index_entry(
{
{
ulint
n_fields
;
ulint
n_fields
;
ulint
low_match
;
ulint
low_match
;
page_t
*
page
;
rec_t
*
rec
;
rec_t
*
rec
;
ut_ad
(
dtuple_check_typed
(
entry
));
ut_ad
(
dtuple_check_typed
(
entry
));
...
@@ -711,11 +708,10 @@ row_search_index_entry(
...
@@ -711,11 +708,10 @@ row_search_index_entry(
low_match
=
btr_pcur_get_low_match
(
pcur
);
low_match
=
btr_pcur_get_low_match
(
pcur
);
rec
=
btr_pcur_get_rec
(
pcur
);
rec
=
btr_pcur_get_rec
(
pcur
);
page
=
buf_frame_align
(
rec
);
n_fields
=
dtuple_get_n_fields
(
entry
);
n_fields
=
dtuple_get_n_fields
(
entry
);
if
(
rec
==
page_get_infimum_rec
(
page
))
{
if
(
page_rec_is_infimum
(
rec
))
{
return
(
FALSE
);
return
(
FALSE
);
}
}
...
...
innobase/row/row0sel.c
View file @
b3d6f517
...
@@ -1261,7 +1261,7 @@ row_sel(
...
@@ -1261,7 +1261,7 @@ row_sel(
/* PHASE 1: Set a lock if specified */
/* PHASE 1: Set a lock if specified */
if
(
!
node
->
asc
&&
cursor_just_opened
if
(
!
node
->
asc
&&
cursor_just_opened
&&
(
rec
!=
page_get_supremum_rec
(
buf_frame_align
(
rec
))
))
{
&&
!
page_rec_is_supremum
(
rec
))
{
/* When we open a cursor for a descending search, we must set
/* When we open a cursor for a descending search, we must set
a next-key lock on the successor record: otherwise it would
a next-key lock on the successor record: otherwise it would
...
@@ -1299,7 +1299,7 @@ row_sel(
...
@@ -1299,7 +1299,7 @@ row_sel(
}
}
}
}
if
(
rec
==
page_get_infimum_rec
(
buf_frame_align
(
rec
)
))
{
if
(
page_rec_is_infimum
(
rec
))
{
/* The infimum record on a page cannot be in the result set,
/* The infimum record on a page cannot be in the result set,
and neither can a record lock be placed on it: we skip such
and neither can a record lock be placed on it: we skip such
...
@@ -1337,7 +1337,7 @@ row_sel(
...
@@ -1337,7 +1337,7 @@ row_sel(
}
}
}
}
if
(
rec
==
page_get_supremum_rec
(
buf_frame_align
(
rec
)
))
{
if
(
page_rec_is_supremum
(
rec
))
{
/* A page supremum record cannot be in the result set: skip
/* A page supremum record cannot be in the result set: skip
it now when we have placed a possible lock on it */
it now when we have placed a possible lock on it */
...
@@ -2416,14 +2416,12 @@ row_sel_store_mysql_rec(
...
@@ -2416,14 +2416,12 @@ row_sel_store_mysql_rec(
mem_heap_t
*
extern_field_heap
=
NULL
;
mem_heap_t
*
extern_field_heap
=
NULL
;
byte
*
data
;
byte
*
data
;
ulint
len
;
ulint
len
;
byte
*
blob_buf
;
int
pad_char
;
ulint
i
;
ulint
i
;
ut_ad
(
prebuilt
->
mysql_template
);
ut_ad
(
prebuilt
->
mysql_template
);
ut_ad
(
rec_offs_validate
(
rec
,
NULL
,
offsets
));
ut_ad
(
rec_offs_validate
(
rec
,
NULL
,
offsets
));
if
(
prebuilt
->
blob_heap
!=
NULL
)
{
if
(
UNIV_LIKELY_NULL
(
prebuilt
->
blob_heap
)
)
{
mem_heap_free
(
prebuilt
->
blob_heap
);
mem_heap_free
(
prebuilt
->
blob_heap
);
prebuilt
->
blob_heap
=
NULL
;
prebuilt
->
blob_heap
=
NULL
;
}
}
...
@@ -2435,7 +2433,8 @@ row_sel_store_mysql_rec(
...
@@ -2435,7 +2433,8 @@ row_sel_store_mysql_rec(
data
=
rec_get_nth_field
(
rec
,
offsets
,
data
=
rec_get_nth_field
(
rec
,
offsets
,
templ
->
rec_field_no
,
&
len
);
templ
->
rec_field_no
,
&
len
);
if
(
rec_offs_nth_extern
(
offsets
,
templ
->
rec_field_no
))
{
if
(
UNIV_UNLIKELY
(
rec_offs_nth_extern
(
offsets
,
templ
->
rec_field_no
)))
{
/* Copy an externally stored field to the temporary
/* Copy an externally stored field to the temporary
heap */
heap */
...
@@ -2456,7 +2455,7 @@ row_sel_store_mysql_rec(
...
@@ -2456,7 +2455,7 @@ row_sel_store_mysql_rec(
}
}
if
(
len
!=
UNIV_SQL_NULL
)
{
if
(
len
!=
UNIV_SQL_NULL
)
{
if
(
templ
->
type
==
DATA_BLOB
)
{
if
(
UNIV_UNLIKELY
(
templ
->
type
==
DATA_BLOB
)
)
{
ut_a
(
prebuilt
->
templ_contains_blob
);
ut_a
(
prebuilt
->
templ_contains_blob
);
...
@@ -2465,8 +2464,9 @@ row_sel_store_mysql_rec(
...
@@ -2465,8 +2464,9 @@ row_sel_store_mysql_rec(
of 1000000 bytes. Since the test takes some
of 1000000 bytes. Since the test takes some
CPU time, we do not use it for small BLOBs. */
CPU time, we do not use it for small BLOBs. */
if
(
len
>
2000000
if
(
UNIV_UNLIKELY
(
len
>
2000000
)
&&
!
ut_test_malloc
(
len
+
1000000
))
{
&&
UNIV_UNLIKELY
(
!
ut_test_malloc
(
len
+
1000000
)))
{
ut_print_timestamp
(
stderr
);
ut_print_timestamp
(
stderr
);
fprintf
(
stderr
,
fprintf
(
stderr
,
...
@@ -2492,11 +2492,9 @@ row_sel_store_mysql_rec(
...
@@ -2492,11 +2492,9 @@ row_sel_store_mysql_rec(
mem_heap_create
(
len
);
mem_heap_create
(
len
);
}
}
blob_buf
=
mem_heap_alloc
(
prebuilt
->
blob_heap
,
data
=
memcpy
(
mem_heap_alloc
(
len
);
prebuilt
->
blob_heap
,
len
),
ut_memcpy
(
blob_buf
,
data
,
len
);
data
,
len
);
data
=
blob_buf
;
}
}
row_sel_field_store_in_mysql_format
(
row_sel_field_store_in_mysql_format
(
...
@@ -2521,41 +2519,45 @@ row_sel_store_mysql_rec(
...
@@ -2521,41 +2519,45 @@ row_sel_store_mysql_rec(
account caused seg faults with NULL BLOB fields, and
account caused seg faults with NULL BLOB fields, and
bug number 154 in the MySQL bug database: GROUP BY
bug number 154 in the MySQL bug database: GROUP BY
and DISTINCT could treat NULL values inequal. */
and DISTINCT could treat NULL values inequal. */
int
pad_char
;
mysql_rec
[
templ
->
mysql_null_byte_offset
]
|=
mysql_rec
[
templ
->
mysql_null_byte_offset
]
|=
(
byte
)
(
templ
->
mysql_null_bit_mask
);
(
byte
)
(
templ
->
mysql_null_bit_mask
);
if
(
templ
->
type
==
DATA_VARCHAR
switch
(
templ
->
type
)
{
||
templ
->
type
==
DATA_CHAR
case
DATA_VARCHAR
:
||
templ
->
type
==
DATA_BINARY
case
DATA_CHAR
:
||
templ
->
type
==
DATA_FIXBINARY
case
DATA_BINARY
:
||
templ
->
type
==
DATA_MYSQL
case
DATA_FIXBINARY
:
||
templ
->
type
==
DATA_VARMYSQL
)
{
case
DATA_MYSQL
:
case
DATA_VARMYSQL
:
/* MySQL pads all non-BLOB and non-TEXT
/* MySQL pads all non-BLOB and non-TEXT
string types with space ' ' */
string types with space ' ' */
if
(
UNIV_UNLIKELY
(
templ
->
mbminlen
==
2
))
{
pad_char
=
' '
;
/* Treat UCS2 as a special case. */
}
else
{
data
=
mysql_rec
pad_char
=
'\0'
;
+
templ
->
mysql_col_offset
;
len
=
templ
->
mysql_col_len
;
/* There are two UCS2 bytes per char,
so the length has to be even. */
ut_a
(
!
(
len
&
1
));
/* Pad with 0x0020. */
while
(
len
)
{
*
data
++
=
0x00
;
*
data
++
=
0x20
;
len
-=
2
;
}
continue
;
}
pad_char
=
0x20
;
break
;
default:
pad_char
=
0x00
;
break
;
}
}
/* Handle UCS2 strings differently. */
ut_ad
(
!
pad_char
||
templ
->
mbminlen
==
1
);
if
(
pad_char
!=
'\0'
&&
templ
->
mbminlen
==
2
)
{
memset
(
mysql_rec
+
templ
->
mysql_col_offset
,
/* There are two bytes per char, so the length
has to be an even number. */
ut_a
(
!
(
templ
->
mysql_col_len
&
1
));
data
=
mysql_rec
+
templ
->
mysql_col_offset
;
len
=
templ
->
mysql_col_len
;
/* Pad with 0x0020. */
while
(
len
>=
2
)
{
*
data
++
=
0x00
;
*
data
++
=
0x20
;
len
-=
2
;
}
}
else
{
ut_ad
(
!
pad_char
||
templ
->
mbminlen
==
1
);
memset
(
mysql_rec
+
templ
->
mysql_col_offset
,
pad_char
,
templ
->
mysql_col_len
);
pad_char
,
templ
->
mysql_col_len
);
}
}
}
}
}
...
@@ -2926,9 +2928,9 @@ row_sel_push_cache_row_for_mysql(
...
@@ -2926,9 +2928,9 @@ row_sel_push_cache_row_for_mysql(
ut_ad
(
prebuilt
->
fetch_cache_first
==
0
);
ut_ad
(
prebuilt
->
fetch_cache_first
==
0
);
if
(
!
row_sel_store_mysql_rec
(
if
(
UNIV_UNLIKELY
(
!
row_sel_store_mysql_rec
(
prebuilt
->
fetch_cache
[
prebuilt
->
n_fetch_cached
],
prebuilt
->
fetch_cache
[
prebuilt
->
n_fetch_cached
],
prebuilt
,
rec
,
offsets
))
{
prebuilt
,
rec
,
offsets
))
)
{
ut_error
;
ut_error
;
}
}
...
@@ -3049,11 +3051,7 @@ row_search_for_mysql(
...
@@ -3049,11 +3051,7 @@ row_search_for_mysql(
rec_t
*
index_rec
;
rec_t
*
index_rec
;
rec_t
*
clust_rec
;
rec_t
*
clust_rec
;
rec_t
*
old_vers
;
rec_t
*
old_vers
;
ulint
err
=
DB_SUCCESS
;
ulint
err
=
DB_SUCCESS
;
ibool
moved
;
ibool
cons_read_requires_clust_rec
;
ibool
was_lock_wait
;
ulint
shortcut
;
ibool
unique_search
=
FALSE
;
ibool
unique_search
=
FALSE
;
ibool
unique_search_from_clust_index
=
FALSE
;
ibool
unique_search_from_clust_index
=
FALSE
;
ibool
mtr_has_extra_clust_latch
=
FALSE
;
ibool
mtr_has_extra_clust_latch
=
FALSE
;
...
@@ -3063,9 +3061,9 @@ row_search_for_mysql(
...
@@ -3063,9 +3061,9 @@ row_search_for_mysql(
locking SELECT, and the isolation
locking SELECT, and the isolation
level is <= TRX_ISO_READ_COMMITTED,
level is <= TRX_ISO_READ_COMMITTED,
then this is set to FALSE */
then this is set to FALSE */
ibool
success
;
#ifdef UNIV_SEARCH_DEBUG
ibool
comp
;
ulint
cnt
=
0
;
ulint
cnt
=
0
;
#endif
/* UNIV_SEARCH_DEBUG */
ulint
next_offs
;
ulint
next_offs
;
mtr_t
mtr
;
mtr_t
mtr
;
mem_heap_t
*
heap
=
NULL
;
mem_heap_t
*
heap
=
NULL
;
...
@@ -3076,7 +3074,7 @@ row_search_for_mysql(
...
@@ -3076,7 +3074,7 @@ row_search_for_mysql(
ut_ad
(
index
&&
pcur
&&
search_tuple
);
ut_ad
(
index
&&
pcur
&&
search_tuple
);
ut_ad
(
trx
->
mysql_thread_id
==
os_thread_get_curr_id
());
ut_ad
(
trx
->
mysql_thread_id
==
os_thread_get_curr_id
());
if
(
prebuilt
->
table
->
ibd_file_missing
)
{
if
(
UNIV_UNLIKELY
(
prebuilt
->
table
->
ibd_file_missing
)
)
{
ut_print_timestamp
(
stderr
);
ut_print_timestamp
(
stderr
);
fprintf
(
stderr
,
" InnoDB: Error:
\n
"
fprintf
(
stderr
,
" InnoDB: Error:
\n
"
"InnoDB: MySQL is trying to use a table handle but the .ibd file for
\n
"
"InnoDB: MySQL is trying to use a table handle but the .ibd file for
\n
"
...
@@ -3090,7 +3088,7 @@ row_search_for_mysql(
...
@@ -3090,7 +3088,7 @@ row_search_for_mysql(
return
(
DB_ERROR
);
return
(
DB_ERROR
);
}
}
if
(
prebuilt
->
magic_n
!=
ROW_PREBUILT_ALLOCATED
)
{
if
(
UNIV_UNLIKELY
(
prebuilt
->
magic_n
!=
ROW_PREBUILT_ALLOCATED
)
)
{
fprintf
(
stderr
,
fprintf
(
stderr
,
"InnoDB: Error: trying to free a corrupt
\n
"
"InnoDB: Error: trying to free a corrupt
\n
"
"InnoDB: table handle. Magic n %lu, table name "
,
"InnoDB: table handle. Magic n %lu, table name "
,
...
@@ -3104,7 +3102,7 @@ row_search_for_mysql(
...
@@ -3104,7 +3102,7 @@ row_search_for_mysql(
}
}
if
(
trx
->
n_mysql_tables_in_use
==
0
if
(
trx
->
n_mysql_tables_in_use
==
0
&&
prebuilt
->
select_lock_type
==
LOCK_NONE
)
{
&&
UNIV_UNLIKELY
(
prebuilt
->
select_lock_type
==
LOCK_NONE
)
)
{
/* Note that if MySQL uses an InnoDB temp table that it
/* Note that if MySQL uses an InnoDB temp table that it
created inside LOCK TABLES, then n_mysql_tables_in_use can
created inside LOCK TABLES, then n_mysql_tables_in_use can
be zero; in that case select_lock_type is set to LOCK_X in
be zero; in that case select_lock_type is set to LOCK_X in
...
@@ -3127,8 +3125,8 @@ row_search_for_mysql(
...
@@ -3127,8 +3125,8 @@ row_search_for_mysql(
/* PHASE 0: Release a possible s-latch we are holding on the
/* PHASE 0: Release a possible s-latch we are holding on the
adaptive hash index latch if there is someone waiting behind */
adaptive hash index latch if there is someone waiting behind */
if
(
trx
->
has_search_latch
if
(
UNIV_UNLIKELY
(
btr_search_latch
.
writer
!=
RW_LOCK_NOT_LOCKED
)
&&
btr_search_latch
.
writer
!=
RW_LOCK_NOT_LOCKED
)
{
&&
trx
->
has_search_latch
)
{
/* There is an x-latch request on the adaptive hash index:
/* There is an x-latch request on the adaptive hash index:
release the s-latch to reduce starvation and wait for
release the s-latch to reduce starvation and wait for
...
@@ -3144,7 +3142,7 @@ row_search_for_mysql(
...
@@ -3144,7 +3142,7 @@ row_search_for_mysql(
/*-------------------------------------------------------------*/
/*-------------------------------------------------------------*/
/* PHASE 1: Try to pop the row from the prefetch cache */
/* PHASE 1: Try to pop the row from the prefetch cache */
if
(
direction
==
0
)
{
if
(
UNIV_UNLIKELY
(
direction
==
0
)
)
{
trx
->
op_info
=
"starting index read"
;
trx
->
op_info
=
"starting index read"
;
prebuilt
->
n_rows_fetched
=
0
;
prebuilt
->
n_rows_fetched
=
0
;
...
@@ -3162,8 +3160,8 @@ row_search_for_mysql(
...
@@ -3162,8 +3160,8 @@ row_search_for_mysql(
prebuilt
->
fetch_direction
=
direction
;
prebuilt
->
fetch_direction
=
direction
;
}
}
if
(
direction
!=
prebuilt
->
fetch_direction
)
{
if
(
UNIV_UNLIKELY
(
direction
!=
prebuilt
->
fetch_direction
)
)
{
if
(
prebuilt
->
n_fetch_cached
>
0
)
{
if
(
UNIV_UNLIKELY
(
prebuilt
->
n_fetch_cached
>
0
)
)
{
ut_error
;
ut_error
;
/* TODO: scrollable cursor: restore cursor to
/* TODO: scrollable cursor: restore cursor to
the place of the latest returned row,
the place of the latest returned row,
...
@@ -3175,7 +3173,7 @@ row_search_for_mysql(
...
@@ -3175,7 +3173,7 @@ row_search_for_mysql(
prebuilt
->
n_fetch_cached
=
0
;
prebuilt
->
n_fetch_cached
=
0
;
prebuilt
->
fetch_cache_first
=
0
;
prebuilt
->
fetch_cache_first
=
0
;
}
else
if
(
prebuilt
->
n_fetch_cached
>
0
)
{
}
else
if
(
UNIV_LIKELY
(
prebuilt
->
n_fetch_cached
>
0
)
)
{
row_sel_pop_cached_row_for_mysql
(
buf
,
prebuilt
);
row_sel_pop_cached_row_for_mysql
(
buf
,
prebuilt
);
prebuilt
->
n_rows_fetched
++
;
prebuilt
->
n_rows_fetched
++
;
...
@@ -3235,7 +3233,8 @@ row_search_for_mysql(
...
@@ -3235,7 +3233,8 @@ row_search_for_mysql(
1 column. Return immediately if this is not a HANDLER
1 column. Return immediately if this is not a HANDLER
command. */
command. */
if
(
direction
!=
0
&&
!
prebuilt
->
used_in_HANDLER
)
{
if
(
UNIV_UNLIKELY
(
direction
!=
0
&&
!
prebuilt
->
used_in_HANDLER
))
{
err
=
DB_RECORD_NOT_FOUND
;
err
=
DB_RECORD_NOT_FOUND
;
goto
func_exit
;
goto
func_exit
;
...
@@ -3253,9 +3252,9 @@ row_search_for_mysql(
...
@@ -3253,9 +3252,9 @@ row_search_for_mysql(
cannot use the adaptive hash index in a search in the case the row
cannot use the adaptive hash index in a search in the case the row
may be long and there may be externally stored fields */
may be long and there may be externally stored fields */
if
(
unique_search
if
(
UNIV_UNLIKELY
(
direction
==
0
)
&&
unique_search
&&
index
->
type
&
DICT_CLUSTERED
&&
index
->
type
&
DICT_CLUSTERED
&&
direction
==
0
&&
!
prebuilt
->
templ_contains_blob
&&
!
prebuilt
->
templ_contains_blob
&&
!
prebuilt
->
used_in_HANDLER
&&
!
prebuilt
->
used_in_HANDLER
&&
(
prebuilt
->
mysql_row_len
<
UNIV_PAGE_SIZE
/
8
))
{
&&
(
prebuilt
->
mysql_row_len
<
UNIV_PAGE_SIZE
/
8
))
{
...
@@ -3287,9 +3286,9 @@ row_search_for_mysql(
...
@@ -3287,9 +3286,9 @@ row_search_for_mysql(
trx
->
has_search_latch
=
TRUE
;
trx
->
has_search_latch
=
TRUE
;
}
}
#endif
#endif
s
hortcut
=
row_sel_try_search_shortcut_for_mysql
(
&
rec
,
s
witch
(
row_sel_try_search_shortcut_for_mysql
(
&
rec
,
prebuilt
,
&
offsets
,
&
heap
,
&
mtr
)
;
prebuilt
,
&
offsets
,
&
heap
,
&
mtr
)
)
{
if
(
shortcut
==
SEL_FOUND
)
{
case
SEL_FOUND
:
#ifdef UNIV_SEARCH_DEBUG
#ifdef UNIV_SEARCH_DEBUG
ut_a
(
0
==
cmp_dtuple_rec
(
search_tuple
,
ut_a
(
0
==
cmp_dtuple_rec
(
search_tuple
,
rec
,
offsets
));
rec
,
offsets
));
...
@@ -3323,9 +3322,8 @@ row_search_for_mysql(
...
@@ -3323,9 +3322,8 @@ row_search_for_mysql(
position */
position */
err
=
DB_SUCCESS
;
err
=
DB_SUCCESS
;
goto
func_exit
;
goto
func_exit
;
}
else
if
(
shortcut
==
SEL_EXHAUSTED
)
{
case
SEL_EXHAUSTED
:
mtr_commit
(
&
mtr
);
mtr_commit
(
&
mtr
);
/* ut_print_name(stderr, index->name);
/* ut_print_name(stderr, index->name);
...
@@ -3368,6 +3366,7 @@ row_search_for_mysql(
...
@@ -3368,6 +3366,7 @@ row_search_for_mysql(
/* Scan the MySQL query string; check if SELECT is the first
/* Scan the MySQL query string; check if SELECT is the first
word there */
word there */
ibool
success
;
dict_accept
(
*
trx
->
mysql_query_str
,
"SELECT"
,
&
success
);
dict_accept
(
*
trx
->
mysql_query_str
,
"SELECT"
,
&
success
);
...
@@ -3383,7 +3382,7 @@ row_search_for_mysql(
...
@@ -3383,7 +3382,7 @@ row_search_for_mysql(
naturally moves upward (in fetch next) in alphabetical order,
naturally moves upward (in fetch next) in alphabetical order,
otherwise downward */
otherwise downward */
if
(
direction
==
0
)
{
if
(
UNIV_UNLIKELY
(
direction
==
0
)
)
{
if
(
mode
==
PAGE_CUR_GE
||
mode
==
PAGE_CUR_G
)
{
if
(
mode
==
PAGE_CUR_GE
||
mode
==
PAGE_CUR_G
)
{
moves_up
=
TRUE
;
moves_up
=
TRUE
;
}
}
...
@@ -3397,10 +3396,9 @@ row_search_for_mysql(
...
@@ -3397,10 +3396,9 @@ row_search_for_mysql(
clust_index
=
dict_table_get_first_index
(
index
->
table
);
clust_index
=
dict_table_get_first_index
(
index
->
table
);
if
(
direction
!=
0
)
{
if
(
UNIV_LIKELY
(
direction
!=
0
))
{
moved
=
sel_restore_position_for_mysql
(
BTR_SEARCH_LEAF
,
pcur
,
if
(
!
sel_restore_position_for_mysql
(
BTR_SEARCH_LEAF
,
pcur
,
moves_up
,
&
mtr
);
moves_up
,
&
mtr
))
{
if
(
!
moved
)
{
goto
next_rec
;
goto
next_rec
;
}
}
...
@@ -3441,11 +3439,13 @@ row_search_for_mysql(
...
@@ -3441,11 +3439,13 @@ row_search_for_mysql(
trx_assign_read_view
(
trx
);
trx_assign_read_view
(
trx
);
prebuilt
->
sql_stat_start
=
FALSE
;
prebuilt
->
sql_stat_start
=
FALSE
;
}
else
{
}
else
{
ulint
lock_mode
;
if
(
prebuilt
->
select_lock_type
==
LOCK_S
)
{
if
(
prebuilt
->
select_lock_type
==
LOCK_S
)
{
err
=
lock_table
(
0
,
index
->
table
,
LOCK_IS
,
thr
)
;
lock_mode
=
LOCK_IS
;
}
else
{
}
else
{
err
=
lock_table
(
0
,
index
->
table
,
LOCK_IX
,
thr
)
;
lock_mode
=
LOCK_IX
;
}
}
err
=
lock_table
(
0
,
index
->
table
,
lock_mode
,
thr
);
if
(
err
!=
DB_SUCCESS
)
{
if
(
err
!=
DB_SUCCESS
)
{
...
@@ -3459,8 +3459,8 @@ row_search_for_mysql(
...
@@ -3459,8 +3459,8 @@ row_search_for_mysql(
/* PHASE 4: Look for matching records in a loop */
/* PHASE 4: Look for matching records in a loop */
rec
=
btr_pcur_get_rec
(
pcur
);
rec
=
btr_pcur_get_rec
(
pcur
);
comp
=
index
->
table
->
comp
;
ut_ad
(
!
page_rec_is_comp
(
rec
)
==
!
index
->
table
->
comp
)
;
ut_ad
(
comp
==
page_is_comp
(
buf_frame_align
(
rec
)));
#ifdef UNIV_SEARCH_DEBUG
/*
/*
fputs("Using ", stderr);
fputs("Using ", stderr);
dict_index_name_print(stderr, index);
dict_index_name_print(stderr, index);
...
@@ -3468,7 +3468,9 @@ row_search_for_mysql(
...
@@ -3468,7 +3468,9 @@ row_search_for_mysql(
buf_frame_get_page_no(buf_frame_align(rec)));
buf_frame_get_page_no(buf_frame_align(rec)));
rec_print(rec);
rec_print(rec);
*/
*/
if
(
rec
==
page_get_infimum_rec
(
buf_frame_align
(
rec
)))
{
#endif
/* UNIV_SEARCH_DEBUG */
if
(
page_rec_is_infimum
(
rec
))
{
/* The infimum record on a page cannot be in the result set,
/* The infimum record on a page cannot be in the result set,
and neither can a record lock be placed on it: we skip such
and neither can a record lock be placed on it: we skip such
...
@@ -3477,10 +3479,11 @@ row_search_for_mysql(
...
@@ -3477,10 +3479,11 @@ row_search_for_mysql(
goto
next_rec
;
goto
next_rec
;
}
}
if
(
rec
==
page_get_supremum_rec
(
buf_frame_align
(
rec
)
))
{
if
(
page_rec_is_supremum
(
rec
))
{
if
(
prebuilt
->
select_lock_type
!=
LOCK_NONE
if
(
set_also_gap_locks
&&
set_also_gap_locks
)
{
&&
!
srv_locks_unsafe_for_binlog
&&
prebuilt
->
select_lock_type
!=
LOCK_NONE
)
{
/* Try to place a lock on the index record */
/* Try to place a lock on the index record */
...
@@ -3488,18 +3491,16 @@ row_search_for_mysql(
...
@@ -3488,18 +3491,16 @@ row_search_for_mysql(
we do not lock gaps. Supremum record is really
we do not lock gaps. Supremum record is really
a gap and therefore we do not set locks there. */
a gap and therefore we do not set locks there. */
if
(
!
srv_locks_unsafe_for_binlog
)
{
offsets
=
rec_get_offsets
(
rec
,
index
,
offsets
,
offsets
=
rec_get_offsets
(
rec
,
index
,
offsets
,
ULINT_UNDEFINED
,
&
heap
);
ULINT_UNDEFINED
,
&
heap
);
err
=
sel_set_rec_lock
(
rec
,
index
,
offsets
,
err
=
sel_set_rec_lock
(
rec
,
index
,
offsets
,
prebuilt
->
select_lock_type
,
prebuilt
->
select_lock_type
,
LOCK_ORDINARY
,
thr
);
LOCK_ORDINARY
,
thr
);
if
(
err
!=
DB_SUCCESS
)
{
goto
lock_wait_or_error
;
if
(
err
!=
DB_SUCCESS
)
{
}
}
goto
lock_wait_or_error
;
}
}
}
/* A page supremum record cannot be in the result set: skip
/* A page supremum record cannot be in the result set: skip
it now that we have placed a possible lock on it */
it now that we have placed a possible lock on it */
...
@@ -3511,12 +3512,19 @@ row_search_for_mysql(
...
@@ -3511,12 +3512,19 @@ row_search_for_mysql(
/* Do sanity checks in case our cursor has bumped into page
/* Do sanity checks in case our cursor has bumped into page
corruption */
corruption */
next_offs
=
rec_get_next_offs
(
rec
,
comp
);
if
(
page_rec_is_comp
(
rec
))
{
next_offs
=
rec_get_next_offs
(
rec
,
TRUE
);
if
(
next_offs
>=
UNIV_PAGE_SIZE
if
(
UNIV_UNLIKELY
(
next_offs
<
PAGE_NEW_SUPREMUM
))
{
||
next_offs
<
goto
wrong_offs
;
(
ulint
)
(
comp
?
PAGE_NEW_SUPREMUM
:
PAGE_OLD_SUPREMUM
))
{
}
}
else
{
next_offs
=
rec_get_next_offs
(
rec
,
FALSE
);
if
(
UNIV_UNLIKELY
(
next_offs
<
PAGE_OLD_SUPREMUM
))
{
goto
wrong_offs
;
}
}
if
(
UNIV_UNLIKELY
(
next_offs
>=
UNIV_PAGE_SIZE
-
PAGE_DIR
))
{
wrong_offs:
if
(
srv_force_recovery
==
0
||
moves_up
==
FALSE
)
{
if
(
srv_force_recovery
==
0
||
moves_up
==
FALSE
)
{
ut_print_timestamp
(
stderr
);
ut_print_timestamp
(
stderr
);
buf_page_print
(
buf_frame_align
(
rec
));
buf_page_print
(
buf_frame_align
(
rec
));
...
@@ -3529,7 +3537,7 @@ row_search_for_mysql(
...
@@ -3529,7 +3537,7 @@ row_search_for_mysql(
fprintf
(
stderr
,
fprintf
(
stderr
,
"InnoDB: Index corruption: rec offs %lu next offs %lu, page no %lu,
\n
"
"InnoDB: Index corruption: rec offs %lu next offs %lu, page no %lu,
\n
"
"InnoDB: "
,
"InnoDB: "
,
(
ulong
)
(
rec
-
buf_frame_align
(
rec
)
),
(
ulong
)
ut_align_offset
(
rec
,
UNIV_PAGE_SIZE
),
(
ulong
)
next_offs
,
(
ulong
)
next_offs
,
(
ulong
)
buf_frame_get_page_no
(
rec
));
(
ulong
)
buf_frame_get_page_no
(
rec
));
dict_index_name_print
(
stderr
,
trx
,
index
);
dict_index_name_print
(
stderr
,
trx
,
index
);
...
@@ -3547,7 +3555,7 @@ row_search_for_mysql(
...
@@ -3547,7 +3555,7 @@ row_search_for_mysql(
fprintf
(
stderr
,
fprintf
(
stderr
,
"InnoDB: Index corruption: rec offs %lu next offs %lu, page no %lu,
\n
"
"InnoDB: Index corruption: rec offs %lu next offs %lu, page no %lu,
\n
"
"InnoDB: "
,
"InnoDB: "
,
(
ulong
)
(
rec
-
buf_frame_align
(
rec
)
),
(
ulong
)
ut_align_offset
(
rec
,
UNIV_PAGE_SIZE
),
(
ulong
)
next_offs
,
(
ulong
)
next_offs
,
(
ulong
)
buf_frame_get_page_no
(
rec
));
(
ulong
)
buf_frame_get_page_no
(
rec
));
dict_index_name_print
(
stderr
,
trx
,
index
);
dict_index_name_print
(
stderr
,
trx
,
index
);
...
@@ -3562,13 +3570,13 @@ row_search_for_mysql(
...
@@ -3562,13 +3570,13 @@ row_search_for_mysql(
offsets
=
rec_get_offsets
(
rec
,
index
,
offsets
,
ULINT_UNDEFINED
,
&
heap
);
offsets
=
rec_get_offsets
(
rec
,
index
,
offsets
,
ULINT_UNDEFINED
,
&
heap
);
if
(
srv_force_recovery
>
0
)
{
if
(
UNIV_UNLIKELY
(
srv_force_recovery
>
0
)
)
{
if
(
!
rec_validate
(
rec
,
offsets
)
if
(
!
rec_validate
(
rec
,
offsets
)
||
!
btr_index_rec_validate
(
rec
,
index
,
FALSE
))
{
||
!
btr_index_rec_validate
(
rec
,
index
,
FALSE
))
{
fprintf
(
stderr
,
fprintf
(
stderr
,
"InnoDB: Index corruption: rec offs %lu next offs %lu, page no %lu,
\n
"
"InnoDB: Index corruption: rec offs %lu next offs %lu, page no %lu,
\n
"
"InnoDB: "
,
"InnoDB: "
,
(
ulong
)
(
rec
-
buf_frame_align
(
rec
)
),
(
ulong
)
ut_align_offset
(
rec
,
UNIV_PAGE_SIZE
),
(
ulong
)
next_offs
,
(
ulong
)
next_offs
,
(
ulong
)
buf_frame_get_page_no
(
rec
));
(
ulong
)
buf_frame_get_page_no
(
rec
));
dict_index_name_print
(
stderr
,
trx
,
index
);
dict_index_name_print
(
stderr
,
trx
,
index
);
...
@@ -3594,25 +3602,22 @@ row_search_for_mysql(
...
@@ -3594,25 +3602,22 @@ row_search_for_mysql(
if
(
0
!=
cmp_dtuple_rec
(
search_tuple
,
rec
,
offsets
))
{
if
(
0
!=
cmp_dtuple_rec
(
search_tuple
,
rec
,
offsets
))
{
if
(
prebuilt
->
select_lock_type
!=
LOCK_NONE
if
(
set_also_gap_locks
&&
set_also_gap_locks
)
{
&&
!
srv_locks_unsafe_for_binlog
&&
prebuilt
->
select_lock_type
!=
LOCK_NONE
)
{
/* Try to place a gap lock on the index
/* Try to place a gap lock on the index
record only if innodb_locks_unsafe_for_binlog
record only if innodb_locks_unsafe_for_binlog
option is not set */
option is not set */
if
(
srv_locks_unsafe_for_binlog
==
FALSE
)
{
err
=
sel_set_rec_lock
(
rec
,
index
,
offsets
,
err
=
sel_set_rec_lock
(
rec
,
index
,
offsets
,
prebuilt
->
select_lock_type
,
prebuilt
->
select_lock_type
,
LOCK_GAP
,
thr
);
LOCK_GAP
,
thr
);
if
(
err
!=
DB_SUCCESS
)
{
goto
lock_wait_or_error
;
if
(
err
!=
DB_SUCCESS
)
{
}
}
goto
lock_wait_or_error
;
}
}
}
btr_pcur_store_position
(
pcur
,
&
mtr
);
btr_pcur_store_position
(
pcur
,
&
mtr
);
...
@@ -3628,25 +3633,22 @@ row_search_for_mysql(
...
@@ -3628,25 +3633,22 @@ row_search_for_mysql(
if
(
!
cmp_dtuple_is_prefix_of_rec
(
search_tuple
,
rec
,
offsets
))
{
if
(
!
cmp_dtuple_is_prefix_of_rec
(
search_tuple
,
rec
,
offsets
))
{
if
(
prebuilt
->
select_lock_type
!=
LOCK_NONE
if
(
set_also_gap_locks
&&
set_also_gap_locks
)
{
&&
!
srv_locks_unsafe_for_binlog
&&
prebuilt
->
select_lock_type
!=
LOCK_NONE
)
{
/* Try to place a gap lock on the index
/* Try to place a gap lock on the index
record only if innodb_locks_unsafe_for_binlog
record only if innodb_locks_unsafe_for_binlog
option is not set */
option is not set */
if
(
srv_locks_unsafe_for_binlog
==
FALSE
)
{
err
=
sel_set_rec_lock
(
rec
,
index
,
offsets
,
err
=
sel_set_rec_lock
(
rec
,
index
,
offsets
,
prebuilt
->
select_lock_type
,
prebuilt
->
select_lock_type
,
LOCK_GAP
,
thr
);
LOCK_GAP
,
thr
);
if
(
err
!=
DB_SUCCESS
)
{
goto
lock_wait_or_error
;
if
(
err
!=
DB_SUCCESS
)
{
}
}
goto
lock_wait_or_error
;
}
}
}
btr_pcur_store_position
(
pcur
,
&
mtr
);
btr_pcur_store_position
(
pcur
,
&
mtr
);
...
@@ -3662,29 +3664,25 @@ row_search_for_mysql(
...
@@ -3662,29 +3664,25 @@ row_search_for_mysql(
/* We are ready to look at a possible new index entry in the result
/* We are ready to look at a possible new index entry in the result
set: the cursor is now placed on a user record */
set: the cursor is now placed on a user record */
cons_read_requires_clust_rec
=
FALSE
;
if
(
prebuilt
->
select_lock_type
!=
LOCK_NONE
)
{
if
(
prebuilt
->
select_lock_type
!=
LOCK_NONE
)
{
/* Try to place a lock on the index record; note that delete
/* Try to place a lock on the index record; note that delete
marked records are a special case in a unique search. If there
marked records are a special case in a unique search. If there
is a non-delete marked record, then it is enough to lock its
is a non-delete marked record, then it is enough to lock its
existence with LOCK_REC_NOT_GAP. */
existence with LOCK_REC_NOT_GAP. */
/* If innodb_locks_unsafe_for_binlog option is used,
we lock only the record, i.e., next-key locking is
not used. */
ulint
lock_type
;
ulint
lock_type
;
if
(
!
set_also_gap_locks
if
(
!
set_also_gap_locks
||
(
unique_search
&&
!
rec_get_deleted_flag
(
rec
,
comp
)))
{
||
srv_locks_unsafe_for_binlog
lock_type
=
LOCK_REC_NOT_GAP
;
||
(
unique_search
&&
!
UNIV_UNLIKELY
(
rec_get_deleted_flag
(
rec
,
page_rec_is_comp
(
rec
)))))
{
goto
no_gap_lock
;
}
else
{
}
else
{
/* If innodb_locks_unsafe_for_binlog option is used,
lock_type
=
LOCK_ORDINARY
;
we lock only the record, i.e., next-key locking is
not used. */
if
(
srv_locks_unsafe_for_binlog
)
{
lock_type
=
LOCK_REC_NOT_GAP
;
}
else
{
lock_type
=
LOCK_ORDINARY
;
}
}
}
/* If we are doing a 'greater or equal than a primary key
/* If we are doing a 'greater or equal than a primary key
...
@@ -3704,7 +3702,7 @@ row_search_for_mysql(
...
@@ -3704,7 +3702,7 @@ row_search_for_mysql(
&&
dtuple_get_n_fields_cmp
(
search_tuple
)
&&
dtuple_get_n_fields_cmp
(
search_tuple
)
==
dict_index_get_n_unique
(
index
)
==
dict_index_get_n_unique
(
index
)
&&
0
==
cmp_dtuple_rec
(
search_tuple
,
rec
,
offsets
))
{
&&
0
==
cmp_dtuple_rec
(
search_tuple
,
rec
,
offsets
))
{
no_gap_lock:
lock_type
=
LOCK_REC_NOT_GAP
;
lock_type
=
LOCK_REC_NOT_GAP
;
}
}
...
@@ -3732,7 +3730,7 @@ row_search_for_mysql(
...
@@ -3732,7 +3730,7 @@ row_search_for_mysql(
high force recovery level set, we try to avoid crashes
high force recovery level set, we try to avoid crashes
by skipping this lookup */
by skipping this lookup */
if
(
srv_force_recovery
<
5
if
(
UNIV_LIKELY
(
srv_force_recovery
<
5
)
&&
!
lock_clust_rec_cons_read_sees
(
rec
,
index
,
&&
!
lock_clust_rec_cons_read_sees
(
rec
,
index
,
offsets
,
trx
->
read_view
))
{
offsets
,
trx
->
read_view
))
{
...
@@ -3763,13 +3761,15 @@ row_search_for_mysql(
...
@@ -3763,13 +3761,15 @@ row_search_for_mysql(
have to look also into the clustered index: this
have to look also into the clustered index: this
is necessary, because we can only get the undo
is necessary, because we can only get the undo
information via the clustered index record. */
information via the clustered index record. */
cons_read_requires_clust_rec
=
TRUE
;
/* Get the clustered index record if needed */
index_rec
=
rec
;
ut_ad
(
index
!=
clust_index
);
goto
requires_clust_rec
;
}
}
}
}
if
(
rec_get_deleted_flag
(
rec
,
comp
)
if
(
UNIV_UNLIKELY
(
rec_get_deleted_flag
(
rec
,
page_rec_is_comp
(
rec
))))
{
&&
!
cons_read_requires_clust_rec
)
{
/* The record is delete-marked: we can skip it if this is
/* The record is delete-marked: we can skip it if this is
not a consistent read which might see an earlier version
not a consistent read which might see an earlier version
...
@@ -3783,14 +3783,14 @@ row_search_for_mysql(
...
@@ -3783,14 +3783,14 @@ row_search_for_mysql(
index_rec
=
rec
;
index_rec
=
rec
;
/* Before and after the following "if" block, "offsets" will be
if
(
index
!=
clust_index
&&
prebuilt
->
need_to_access_clustered
)
{
re
lated to "rec", which may be in "index", a secondary index or
re
quires_clust_rec:
the clustered index ("clust_index"). However, after this "if" block,
/* Before and after this "if" block, "offsets" will be
"rec" may be pointing to "clust_rec" of "clust_index". */
related to "rec", which may be in a secondary index "index" or
ut_ad
(
rec_offs_validate
(
rec
,
index
,
offsets
));
the clustered index ("clust_index"). However, after this
"if" block, "rec" may be pointing to
if
(
index
!=
clust_index
&&
(
cons_read_requires_clust_rec
"clust_rec" of "clust_index". */
||
prebuilt
->
need_to_access_clustered
))
{
ut_ad
(
rec_offs_validate
(
rec
,
index
,
offsets
));
/* It was a non-clustered index and we must fetch also the
/* It was a non-clustered index and we must fetch also the
clustered index record */
clustered index record */
...
@@ -3812,7 +3812,8 @@ row_search_for_mysql(
...
@@ -3812,7 +3812,8 @@ row_search_for_mysql(
goto
next_rec
;
goto
next_rec
;
}
}
if
(
rec_get_deleted_flag
(
clust_rec
,
comp
))
{
if
(
UNIV_UNLIKELY
(
rec_get_deleted_flag
(
clust_rec
,
page_rec_is_comp
(
clust_rec
))))
{
/* The record is delete marked: we can skip it */
/* The record is delete marked: we can skip it */
...
@@ -3833,7 +3834,8 @@ row_search_for_mysql(
...
@@ -3833,7 +3834,8 @@ row_search_for_mysql(
rec
==
clust_rec
?
clust_index
:
index
,
rec
==
clust_rec
?
clust_index
:
index
,
offsets
));
offsets
));
if
(
prebuilt
->
n_rows_fetched
>=
MYSQL_FETCH_CACHE_THRESHOLD
if
((
match_mode
==
ROW_SEL_EXACT
||
prebuilt
->
n_rows_fetched
>=
MYSQL_FETCH_CACHE_THRESHOLD
)
&&
prebuilt
->
select_lock_type
==
LOCK_NONE
&&
prebuilt
->
select_lock_type
==
LOCK_NONE
&&
!
prebuilt
->
templ_contains_blob
&&
!
prebuilt
->
templ_contains_blob
&&
!
prebuilt
->
clust_index_was_generated
&&
!
prebuilt
->
clust_index_was_generated
...
@@ -3908,7 +3910,7 @@ row_search_for_mysql(
...
@@ -3908,7 +3910,7 @@ row_search_for_mysql(
/*-------------------------------------------------------------*/
/*-------------------------------------------------------------*/
/* PHASE 5: Move the cursor to the next index record */
/* PHASE 5: Move the cursor to the next index record */
if
(
mtr_has_extra_clust_latch
)
{
if
(
UNIV_UNLIKELY
(
mtr_has_extra_clust_latch
)
)
{
/* We must commit mtr if we are moving to the next
/* We must commit mtr if we are moving to the next
non-clustered index record, because we could break the
non-clustered index record, because we could break the
latching order if we would access a different clustered
latching order if we would access a different clustered
...
@@ -3920,34 +3922,38 @@ row_search_for_mysql(
...
@@ -3920,34 +3922,38 @@ row_search_for_mysql(
mtr_has_extra_clust_latch
=
FALSE
;
mtr_has_extra_clust_latch
=
FALSE
;
mtr_start
(
&
mtr
);
mtr_start
(
&
mtr
);
moved
=
sel_restore_position_for_mysql
(
BTR_SEARCH_LEAF
,
pcur
,
if
(
sel_restore_position_for_mysql
(
BTR_SEARCH_LEAF
,
pcur
,
moves_up
,
&
mtr
)
;
moves_up
,
&
mtr
)
)
{
if
(
moved
)
{
#ifdef UNIV_SEARCH_DEBUG
cnt
++
;
cnt
++
;
#endif
/* UNIV_SEARCH_DEBUG */
goto
rec_loop
;
goto
rec_loop
;
}
}
}
}
if
(
moves_up
)
{
if
(
moves_up
)
{
moved
=
btr_pcur_move_to_next
(
pcur
,
&
mtr
);
if
(
UNIV_UNLIKELY
(
!
btr_pcur_move_to_next
(
pcur
,
&
mtr
)))
{
}
else
{
not_moved:
moved
=
btr_pcur_move_to_prev
(
pcur
,
&
mtr
);
btr_pcur_store_position
(
pcur
,
&
mtr
);
}
if
(
!
moved
)
{
if
(
match_mode
!=
0
)
{
btr_pcur_store_position
(
pcur
,
&
mtr
);
err
=
DB_RECORD_NOT_FOUND
;
}
else
{
err
=
DB_END_OF_INDEX
;
}
if
(
match_mode
!=
0
)
{
goto
normal_return
;
err
=
DB_RECORD_NOT_FOUND
;
}
}
else
{
}
else
{
err
=
DB_END_OF_INDEX
;
if
(
UNIV_UNLIKELY
(
!
btr_pcur_move_to_prev
(
pcur
,
&
mtr
)))
{
goto
not_moved
;
}
}
goto
normal_return
;
}
}
#ifdef UNIV_SEARCH_DEBUG
cnt
++
;
cnt
++
;
#endif
/* UNIV_SEARCH_DEBUG */
goto
rec_loop
;
goto
rec_loop
;
...
@@ -3965,11 +3971,10 @@ row_search_for_mysql(
...
@@ -3965,11 +3971,10 @@ row_search_for_mysql(
que_thr_stop_for_mysql
(
thr
);
que_thr_stop_for_mysql
(
thr
);
thr
->
lock_state
=
QUE_THR_LOCK_ROW
;
thr
->
lock_state
=
QUE_THR_LOCK_ROW
;
was_lock_wait
=
row_mysql_handle_errors
(
&
err
,
trx
,
thr
,
NULL
);
thr
->
lock_state
=
QUE_THR_LOCK_NOLOCK
;
if
(
was_lock_wait
)
{
if
(
row_mysql_handle_errors
(
&
err
,
trx
,
thr
,
NULL
))
{
thr
->
lock_state
=
QUE_THR_LOCK_NOLOCK
;
mtr_start
(
&
mtr
);
mtr_start
(
&
mtr
);
sel_restore_position_for_mysql
(
BTR_SEARCH_LEAF
,
pcur
,
sel_restore_position_for_mysql
(
BTR_SEARCH_LEAF
,
pcur
,
...
@@ -3979,9 +3984,13 @@ row_search_for_mysql(
...
@@ -3979,9 +3984,13 @@ row_search_for_mysql(
goto
rec_loop
;
goto
rec_loop
;
}
}
thr
->
lock_state
=
QUE_THR_LOCK_NOLOCK
;
#ifdef UNIV_SEARCH_DEBUG
/* fputs("Using ", stderr);
/* fputs("Using ", stderr);
dict_index_name_print(stderr, index);
dict_index_name_print(stderr, index);
fprintf(stderr, " cnt %lu ret value %lu err\n", cnt, err); */
fprintf(stderr, " cnt %lu ret value %lu err\n", cnt, err); */
#endif
/* UNIV_SEARCH_DEBUG */
goto
func_exit
;
goto
func_exit
;
normal_return:
normal_return:
...
@@ -3996,9 +4005,11 @@ row_search_for_mysql(
...
@@ -3996,9 +4005,11 @@ row_search_for_mysql(
err
=
DB_SUCCESS
;
err
=
DB_SUCCESS
;
}
}
#ifdef UNIV_SEARCH_DEBUG
/* fputs("Using ", stderr);
/* fputs("Using ", stderr);
dict_index_name_print(stderr, index);
dict_index_name_print(stderr, index);
fprintf(stderr, " cnt %lu ret value %lu err\n", cnt, err); */
fprintf(stderr, " cnt %lu ret value %lu err\n", cnt, err); */
#endif
/* UNIV_SEARCH_DEBUG */
if
(
err
==
DB_SUCCESS
)
{
if
(
err
==
DB_SUCCESS
)
{
srv_n_rows_read
++
;
srv_n_rows_read
++
;
}
}
...
...
innobase/row/row0vers.c
View file @
b3d6f517
...
@@ -61,7 +61,7 @@ row_vers_impl_x_locked_off_kernel(
...
@@ -61,7 +61,7 @@ row_vers_impl_x_locked_off_kernel(
ibool
rec_del
;
ibool
rec_del
;
ulint
err
;
ulint
err
;
mtr_t
mtr
;
mtr_t
mtr
;
ibool
comp
;
ulint
comp
;
#ifdef UNIV_SYNC_DEBUG
#ifdef UNIV_SYNC_DEBUG
ut_ad
(
mutex_own
(
&
kernel_mutex
));
ut_ad
(
mutex_own
(
&
kernel_mutex
));
...
@@ -121,10 +121,10 @@ row_vers_impl_x_locked_off_kernel(
...
@@ -121,10 +121,10 @@ row_vers_impl_x_locked_off_kernel(
goto
exit_func
;
goto
exit_func
;
}
}
comp
=
index
->
table
->
comp
;
comp
=
page_rec_is_comp
(
rec
)
;
ut_ad
(
index
->
table
==
clust_index
->
table
);
ut_ad
(
index
->
table
==
clust_index
->
table
);
ut_ad
(
comp
==
page_is_comp
(
buf_frame_align
(
rec
))
);
ut_ad
(
!!
comp
==
index
->
table
->
comp
);
ut_ad
(
comp
==
page_is_comp
(
buf_frame_align
(
clust_rec
)
));
ut_ad
(
!
comp
==
!
page_rec_is_comp
(
clust_rec
));
/* We look up if some earlier version, which was modified by the trx_id
/* We look up if some earlier version, which was modified by the trx_id
transaction, of the clustered index record would require rec to be in
transaction, of the clustered index record would require rec to be in
...
@@ -310,7 +310,7 @@ row_vers_old_has_index_entry(
...
@@ -310,7 +310,7 @@ row_vers_old_has_index_entry(
dtuple_t
*
row
;
dtuple_t
*
row
;
dtuple_t
*
entry
;
dtuple_t
*
entry
;
ulint
err
;
ulint
err
;
ibool
comp
;
ulint
comp
;
ut_ad
(
mtr_memo_contains
(
mtr
,
buf_block_align
(
rec
),
MTR_MEMO_PAGE_X_FIX
)
ut_ad
(
mtr_memo_contains
(
mtr
,
buf_block_align
(
rec
),
MTR_MEMO_PAGE_X_FIX
)
||
mtr_memo_contains
(
mtr
,
buf_block_align
(
rec
),
||
mtr_memo_contains
(
mtr
,
buf_block_align
(
rec
),
...
@@ -322,8 +322,8 @@ row_vers_old_has_index_entry(
...
@@ -322,8 +322,8 @@ row_vers_old_has_index_entry(
clust_index
=
dict_table_get_first_index
(
index
->
table
);
clust_index
=
dict_table_get_first_index
(
index
->
table
);
comp
=
index
->
table
->
comp
;
comp
=
page_rec_is_comp
(
rec
)
;
ut_ad
(
comp
==
page_is_comp
(
buf_frame_align
(
rec
))
);
ut_ad
(
!
index
->
table
->
comp
==
!
comp
);
heap
=
mem_heap_create
(
1024
);
heap
=
mem_heap_create
(
1024
);
clust_offsets
=
rec_get_offsets
(
rec
,
clust_index
,
NULL
,
clust_offsets
=
rec_get_offsets
(
rec
,
clust_index
,
NULL
,
ULINT_UNDEFINED
,
&
heap
);
ULINT_UNDEFINED
,
&
heap
);
...
...
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment