Commit 855c2aa8 authored by marko's avatar marko

branches/zip: btr0btr.c: Add more UNIV_BTR_DEBUG checks. This should

help in tracking down issue #63 (memory corruption).  UNIV_BTR_DEBUG
is currently enabled in univ.i.

btr_root_fseg_validate(): New function, for validating a file segment
header on a B-tree root page.

btr_root_block_get(), btr_free_but_not_root(),
btr_root_raise_and_insert(), btr_discard_only_page_on_level():
Check PAGE_BTR_SEG_LEAF and PAGE_BTR_SEG_TOP on the root page with
btr_root_fseg_validate().

btr_root_raise_and_insert(): Move the assertion
dict_index_get_page(index) == page_get_page_no(root)
inside UNIV_BTR_DEBUG.  It was previously enabled by UNIV_DEBUG.

btr_free_root(): Check PAGE_BTR_SEG_TOP on the root page with
btr_root_fseg_validate().
parent 46b312cd
...@@ -78,6 +78,26 @@ make them consecutive on disk if possible. From the other file segment ...@@ -78,6 +78,26 @@ make them consecutive on disk if possible. From the other file segment
we allocate pages for the non-leaf levels of the tree. we allocate pages for the non-leaf levels of the tree.
*/ */
#ifdef UNIV_BTR_DEBUG
/******************************************************************
Checks a file segment header within a B-tree root page. */
static
ibool
btr_root_fseg_validate(
/*===================*/
/* out: TRUE if valid */
const fseg_header_t* seg_header, /* in: segment header */
ulint space) /* in: tablespace identifier */
{
ulint offset = mach_read_from_2(seg_header + FSEG_HDR_OFFSET);
ut_a(mach_read_from_4(seg_header + FSEG_HDR_SPACE) == space);
ut_a(offset >= FIL_PAGE_DATA);
ut_a(offset <= UNIV_PAGE_SIZE - FIL_PAGE_DATA_END);
return(TRUE);
}
#endif /* UNIV_BTR_DEBUG */
/****************************************************************** /******************************************************************
Gets the root node of a tree and x-latches it. */ Gets the root node of a tree and x-latches it. */
static static
...@@ -100,6 +120,12 @@ btr_root_block_get( ...@@ -100,6 +120,12 @@ btr_root_block_get(
block = btr_block_get(space, zip_size, root_page_no, RW_X_LATCH, mtr); block = btr_block_get(space, zip_size, root_page_no, RW_X_LATCH, mtr);
ut_a((ibool)!!page_is_comp(buf_block_get_frame(block)) ut_a((ibool)!!page_is_comp(buf_block_get_frame(block))
== dict_table_is_comp(index->table)); == dict_table_is_comp(index->table));
#ifdef UNIV_BTR_DEBUG
ut_a(btr_root_fseg_validate(FIL_PAGE_DATA + PAGE_BTR_SEG_LEAF
+ buf_block_get_frame(block), space));
ut_a(btr_root_fseg_validate(FIL_PAGE_DATA + PAGE_BTR_SEG_TOP
+ buf_block_get_frame(block), space));
#endif /* UNIV_BTR_DEBUG */
return(block); return(block);
} }
...@@ -820,6 +846,12 @@ leaf_loop: ...@@ -820,6 +846,12 @@ leaf_loop:
mtr_start(&mtr); mtr_start(&mtr);
root = btr_page_get(space, zip_size, root_page_no, RW_X_LATCH, &mtr); root = btr_page_get(space, zip_size, root_page_no, RW_X_LATCH, &mtr);
#ifdef UNIV_BTR_DEBUG
ut_a(btr_root_fseg_validate(FIL_PAGE_DATA + PAGE_BTR_SEG_LEAF
+ root, space));
ut_a(btr_root_fseg_validate(FIL_PAGE_DATA + PAGE_BTR_SEG_TOP
+ root, space));
#endif /* UNIV_BTR_DEBUG */
/* NOTE: page hash indexes are dropped when a page is freed inside /* NOTE: page hash indexes are dropped when a page is freed inside
fsp0fsp. */ fsp0fsp. */
...@@ -836,6 +868,10 @@ top_loop: ...@@ -836,6 +868,10 @@ top_loop:
mtr_start(&mtr); mtr_start(&mtr);
root = btr_page_get(space, zip_size, root_page_no, RW_X_LATCH, &mtr); root = btr_page_get(space, zip_size, root_page_no, RW_X_LATCH, &mtr);
#ifdef UNIV_BTR_DEBUG
ut_a(btr_root_fseg_validate(FIL_PAGE_DATA + PAGE_BTR_SEG_TOP
+ root, space));
#endif /* UNIV_BTR_DEBUG */
finished = fseg_free_step_not_header( finished = fseg_free_step_not_header(
root + PAGE_HEADER + PAGE_BTR_SEG_TOP, &mtr); root + PAGE_HEADER + PAGE_BTR_SEG_TOP, &mtr);
...@@ -868,6 +904,9 @@ btr_free_root( ...@@ -868,6 +904,9 @@ btr_free_root(
btr_search_drop_page_hash_index(block); btr_search_drop_page_hash_index(block);
header = buf_block_get_frame(block) + PAGE_HEADER + PAGE_BTR_SEG_TOP; header = buf_block_get_frame(block) + PAGE_HEADER + PAGE_BTR_SEG_TOP;
#ifdef UNIV_BTR_DEBUG
ut_a(btr_root_fseg_validate(header, space));
#endif /* UNIV_BTR_DEBUG */
while (!fseg_free_step(header, mtr)); while (!fseg_free_step(header, mtr));
} }
...@@ -1104,8 +1143,13 @@ btr_root_raise_and_insert( ...@@ -1104,8 +1143,13 @@ btr_root_raise_and_insert(
ut_a(!root_page_zip || page_zip_validate(root_page_zip, root)); ut_a(!root_page_zip || page_zip_validate(root_page_zip, root));
#endif /* UNIV_ZIP_DEBUG */ #endif /* UNIV_ZIP_DEBUG */
index = btr_cur_get_index(cursor); index = btr_cur_get_index(cursor);
#ifdef UNIV_BTR_DEBUG
ut_ad(dict_index_get_page(index) == page_get_page_no(root)); ut_a(btr_root_fseg_validate(FIL_PAGE_DATA + PAGE_BTR_SEG_LEAF
+ root, dict_index_get_space(index)));
ut_a(btr_root_fseg_validate(FIL_PAGE_DATA + PAGE_BTR_SEG_TOP
+ root, dict_index_get_space(index)));
ut_a(dict_index_get_page(index) == page_get_page_no(root));
#endif /* UNIV_BTR_DEBUG */
ut_ad(mtr_memo_contains(mtr, dict_index_get_lock(index), ut_ad(mtr_memo_contains(mtr, dict_index_get_lock(index),
MTR_MEMO_X_LOCK)); MTR_MEMO_X_LOCK));
ut_ad(mtr_memo_contains(mtr, root_block, MTR_MEMO_PAGE_X_FIX)); ut_ad(mtr_memo_contains(mtr, root_block, MTR_MEMO_PAGE_X_FIX));
...@@ -2651,6 +2695,14 @@ btr_discard_only_page_on_level( ...@@ -2651,6 +2695,14 @@ btr_discard_only_page_on_level(
== dict_index_get_page(index))) { == dict_index_get_page(index))) {
/* The father is the root page */ /* The father is the root page */
#ifdef UNIV_BTR_DEBUG
const page_t* root = buf_block_get_frame(father_block);
const ulint space = dict_index_get_space(index);
ut_a(btr_root_fseg_validate(FIL_PAGE_DATA + PAGE_BTR_SEG_LEAF
+ root, space));
ut_a(btr_root_fseg_validate(FIL_PAGE_DATA + PAGE_BTR_SEG_TOP
+ root, space));
#endif /* UNIV_BTR_DEBUG */
btr_page_empty(father_block, father_page_zip, mtr, index); btr_page_empty(father_block, father_page_zip, mtr, index);
/* We play safe and reset the free bits for the father */ /* We play safe and reset the free bits for the father */
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment