diff options
Diffstat (limited to 'storage/innobase/fut/fut0lst.cc')
-rw-r--r-- | storage/innobase/fut/fut0lst.cc | 212 |
1 files changed, 137 insertions, 75 deletions
diff --git a/storage/innobase/fut/fut0lst.cc b/storage/innobase/fut/fut0lst.cc index 8f96a6426d2..8b39a4de1fb 100644 --- a/storage/innobase/fut/fut0lst.cc +++ b/storage/innobase/fut/fut0lst.cc @@ -1,6 +1,6 @@ /***************************************************************************** -Copyright (c) 1995, 2011, Oracle and/or its affiliates. All Rights Reserved. +Copyright (c) 1995, 2014, Oracle and/or its affiliates. All Rights Reserved. This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software @@ -23,6 +23,7 @@ File-based list utilities Created 11/28/1995 Heikki Tuuri ***********************************************************************/ +#include "univ.i" #include "fut0lst.h" #ifdef UNIV_NONINL @@ -49,9 +50,13 @@ flst_add_to_empty( ut_ad(mtr && base && node); ut_ad(base != node); - ut_ad(mtr_memo_contains_page(mtr, base, MTR_MEMO_PAGE_X_FIX)); - ut_ad(mtr_memo_contains_page(mtr, node, MTR_MEMO_PAGE_X_FIX)); - len = flst_get_len(base, mtr); + ut_ad(mtr_memo_contains_page_flagged(mtr, base, + MTR_MEMO_PAGE_X_FIX + | MTR_MEMO_PAGE_SX_FIX)); + ut_ad(mtr_memo_contains_page_flagged(mtr, node, + MTR_MEMO_PAGE_X_FIX + | MTR_MEMO_PAGE_SX_FIX)); + len = flst_get_len(base); ut_a(len == 0); buf_ptr_get_fsp_addr(node, &space, &node_addr); @@ -70,7 +75,6 @@ flst_add_to_empty( /********************************************************************//** Adds a node as the last node in a list. */ -UNIV_INTERN void flst_add_last( /*==========*/ @@ -82,26 +86,35 @@ flst_add_last( fil_addr_t node_addr; ulint len; fil_addr_t last_addr; - flst_node_t* last_node; ut_ad(mtr && base && node); ut_ad(base != node); - ut_ad(mtr_memo_contains_page(mtr, base, MTR_MEMO_PAGE_X_FIX)); - ut_ad(mtr_memo_contains_page(mtr, node, MTR_MEMO_PAGE_X_FIX)); - len = flst_get_len(base, mtr); + ut_ad(mtr_memo_contains_page_flagged(mtr, base, + MTR_MEMO_PAGE_X_FIX + | MTR_MEMO_PAGE_SX_FIX)); + ut_ad(mtr_memo_contains_page_flagged(mtr, node, + MTR_MEMO_PAGE_X_FIX + | MTR_MEMO_PAGE_SX_FIX)); + len = flst_get_len(base); last_addr = flst_get_last(base, mtr); buf_ptr_get_fsp_addr(node, &space, &node_addr); /* If the list is not empty, call flst_insert_after */ if (len != 0) { + flst_node_t* last_node; + if (last_addr.page == node_addr.page) { last_node = page_align(node) + last_addr.boffset; } else { - ulint zip_size = fil_space_get_zip_size(space); + bool found; + const page_size_t& page_size + = fil_space_get_page_size(space, &found); + + ut_ad(found); - last_node = fut_get_ptr(space, zip_size, last_addr, - RW_X_LATCH, mtr); + last_node = fut_get_ptr(space, page_size, last_addr, + RW_SX_LATCH, mtr); } flst_insert_after(base, last_node, node, mtr); @@ -113,7 +126,6 @@ flst_add_last( /********************************************************************//** Adds a node as the first node in a list. */ -UNIV_INTERN void flst_add_first( /*===========*/ @@ -129,9 +141,13 @@ flst_add_first( ut_ad(mtr && base && node); ut_ad(base != node); - ut_ad(mtr_memo_contains_page(mtr, base, MTR_MEMO_PAGE_X_FIX)); - ut_ad(mtr_memo_contains_page(mtr, node, MTR_MEMO_PAGE_X_FIX)); - len = flst_get_len(base, mtr); + ut_ad(mtr_memo_contains_page_flagged(mtr, base, + MTR_MEMO_PAGE_X_FIX + | MTR_MEMO_PAGE_SX_FIX)); + ut_ad(mtr_memo_contains_page_flagged(mtr, node, + MTR_MEMO_PAGE_X_FIX + | MTR_MEMO_PAGE_SX_FIX)); + len = flst_get_len(base); first_addr = flst_get_first(base, mtr); buf_ptr_get_fsp_addr(node, &space, &node_addr); @@ -141,10 +157,14 @@ flst_add_first( if (first_addr.page == node_addr.page) { first_node = page_align(node) + first_addr.boffset; } else { - ulint zip_size = fil_space_get_zip_size(space); + bool found; + const page_size_t& page_size + = fil_space_get_page_size(space, &found); + + ut_ad(found); - first_node = fut_get_ptr(space, zip_size, first_addr, - RW_X_LATCH, mtr); + first_node = fut_get_ptr(space, page_size, first_addr, + RW_SX_LATCH, mtr); } flst_insert_before(base, node, first_node, mtr); @@ -156,7 +176,6 @@ flst_add_first( /********************************************************************//** Inserts a node after another in a list. */ -UNIV_INTERN void flst_insert_after( /*==============*/ @@ -176,9 +195,15 @@ flst_insert_after( ut_ad(base != node1); ut_ad(base != node2); ut_ad(node2 != node1); - ut_ad(mtr_memo_contains_page(mtr, base, MTR_MEMO_PAGE_X_FIX)); - ut_ad(mtr_memo_contains_page(mtr, node1, MTR_MEMO_PAGE_X_FIX)); - ut_ad(mtr_memo_contains_page(mtr, node2, MTR_MEMO_PAGE_X_FIX)); + ut_ad(mtr_memo_contains_page_flagged(mtr, base, + MTR_MEMO_PAGE_X_FIX + | MTR_MEMO_PAGE_SX_FIX)); + ut_ad(mtr_memo_contains_page_flagged(mtr, node1, + MTR_MEMO_PAGE_X_FIX + | MTR_MEMO_PAGE_SX_FIX)); + ut_ad(mtr_memo_contains_page_flagged(mtr, node2, + MTR_MEMO_PAGE_X_FIX + | MTR_MEMO_PAGE_SX_FIX)); buf_ptr_get_fsp_addr(node1, &space, &node1_addr); buf_ptr_get_fsp_addr(node2, &space, &node2_addr); @@ -191,10 +216,14 @@ flst_insert_after( if (!fil_addr_is_null(node3_addr)) { /* Update prev field of node3 */ - ulint zip_size = fil_space_get_zip_size(space); + bool found; + const page_size_t& page_size + = fil_space_get_page_size(space, &found); - node3 = fut_get_ptr(space, zip_size, - node3_addr, RW_X_LATCH, mtr); + ut_ad(found); + + node3 = fut_get_ptr(space, page_size, + node3_addr, RW_SX_LATCH, mtr); flst_write_addr(node3 + FLST_PREV, node2_addr, mtr); } else { /* node1 was last in list: update last field in base */ @@ -205,13 +234,12 @@ flst_insert_after( flst_write_addr(node1 + FLST_NEXT, node2_addr, mtr); /* Update len of base node */ - len = flst_get_len(base, mtr); + len = flst_get_len(base); mlog_write_ulint(base + FLST_LEN, len + 1, MLOG_4BYTES, mtr); } /********************************************************************//** Inserts a node before another in a list. */ -UNIV_INTERN void flst_insert_before( /*===============*/ @@ -231,9 +259,15 @@ flst_insert_before( ut_ad(base != node2); ut_ad(base != node3); ut_ad(node2 != node3); - ut_ad(mtr_memo_contains_page(mtr, base, MTR_MEMO_PAGE_X_FIX)); - ut_ad(mtr_memo_contains_page(mtr, node2, MTR_MEMO_PAGE_X_FIX)); - ut_ad(mtr_memo_contains_page(mtr, node3, MTR_MEMO_PAGE_X_FIX)); + ut_ad(mtr_memo_contains_page_flagged(mtr, base, + MTR_MEMO_PAGE_X_FIX + | MTR_MEMO_PAGE_SX_FIX)); + ut_ad(mtr_memo_contains_page_flagged(mtr, node2, + MTR_MEMO_PAGE_X_FIX + | MTR_MEMO_PAGE_SX_FIX)); + ut_ad(mtr_memo_contains_page_flagged(mtr, node3, + MTR_MEMO_PAGE_X_FIX + | MTR_MEMO_PAGE_SX_FIX)); buf_ptr_get_fsp_addr(node2, &space, &node2_addr); buf_ptr_get_fsp_addr(node3, &space, &node3_addr); @@ -245,10 +279,15 @@ flst_insert_before( flst_write_addr(node2 + FLST_NEXT, node3_addr, mtr); if (!fil_addr_is_null(node1_addr)) { - ulint zip_size = fil_space_get_zip_size(space); + bool found; + const page_size_t& page_size + = fil_space_get_page_size(space, &found); + + ut_ad(found); + /* Update next field of node1 */ - node1 = fut_get_ptr(space, zip_size, node1_addr, - RW_X_LATCH, mtr); + node1 = fut_get_ptr(space, page_size, node1_addr, + RW_SX_LATCH, mtr); flst_write_addr(node1 + FLST_NEXT, node2_addr, mtr); } else { /* node3 was first in list: update first field in base */ @@ -259,13 +298,12 @@ flst_insert_before( flst_write_addr(node3 + FLST_PREV, node2_addr, mtr); /* Update len of base node */ - len = flst_get_len(base, mtr); + len = flst_get_len(base); mlog_write_ulint(base + FLST_LEN, len + 1, MLOG_4BYTES, mtr); } /********************************************************************//** Removes a node. */ -UNIV_INTERN void flst_remove( /*========*/ @@ -274,7 +312,6 @@ flst_remove( mtr_t* mtr) /*!< in: mini-transaction handle */ { ulint space; - ulint zip_size; flst_node_t* node1; fil_addr_t node1_addr; fil_addr_t node2_addr; @@ -283,11 +320,20 @@ flst_remove( ulint len; ut_ad(mtr && node2 && base); - ut_ad(mtr_memo_contains_page(mtr, base, MTR_MEMO_PAGE_X_FIX)); - ut_ad(mtr_memo_contains_page(mtr, node2, MTR_MEMO_PAGE_X_FIX)); + ut_ad(mtr_memo_contains_page_flagged(mtr, base, + MTR_MEMO_PAGE_X_FIX + | MTR_MEMO_PAGE_SX_FIX)); + ut_ad(mtr_memo_contains_page_flagged(mtr, node2, + MTR_MEMO_PAGE_X_FIX + | MTR_MEMO_PAGE_SX_FIX)); buf_ptr_get_fsp_addr(node2, &space, &node2_addr); - zip_size = fil_space_get_zip_size(space); + + bool found; + const page_size_t& page_size = fil_space_get_page_size(space, + &found); + + ut_ad(found); node1_addr = flst_get_prev_addr(node2, mtr); node3_addr = flst_get_next_addr(node2, mtr); @@ -300,8 +346,8 @@ flst_remove( node1 = page_align(node2) + node1_addr.boffset; } else { - node1 = fut_get_ptr(space, zip_size, - node1_addr, RW_X_LATCH, mtr); + node1 = fut_get_ptr(space, page_size, + node1_addr, RW_SX_LATCH, mtr); } ut_ad(node1 != node2); @@ -319,8 +365,8 @@ flst_remove( node3 = page_align(node2) + node3_addr.boffset; } else { - node3 = fut_get_ptr(space, zip_size, - node3_addr, RW_X_LATCH, mtr); + node3 = fut_get_ptr(space, page_size, + node3_addr, RW_SX_LATCH, mtr); } ut_ad(node2 != node3); @@ -332,7 +378,7 @@ flst_remove( } /* Update len of base node */ - len = flst_get_len(base, mtr); + len = flst_get_len(base); ut_ad(len > 0); mlog_write_ulint(base + FLST_LEN, len - 1, MLOG_4BYTES, mtr); @@ -342,7 +388,6 @@ flst_remove( Cuts off the tail of the list, including the node given. The number of nodes which will be removed must be provided by the caller, as this function does not measure the length of the tail. */ -UNIV_INTERN void flst_cut_end( /*=========*/ @@ -359,8 +404,12 @@ flst_cut_end( ulint len; ut_ad(mtr && node2 && base); - ut_ad(mtr_memo_contains_page(mtr, base, MTR_MEMO_PAGE_X_FIX)); - ut_ad(mtr_memo_contains_page(mtr, node2, MTR_MEMO_PAGE_X_FIX)); + ut_ad(mtr_memo_contains_page_flagged(mtr, base, + MTR_MEMO_PAGE_X_FIX + | MTR_MEMO_PAGE_SX_FIX)); + ut_ad(mtr_memo_contains_page_flagged(mtr, node2, + MTR_MEMO_PAGE_X_FIX + | MTR_MEMO_PAGE_SX_FIX)); ut_ad(n_nodes > 0); buf_ptr_get_fsp_addr(node2, &space, &node2_addr); @@ -375,9 +424,14 @@ flst_cut_end( node1 = page_align(node2) + node1_addr.boffset; } else { - node1 = fut_get_ptr(space, - fil_space_get_zip_size(space), - node1_addr, RW_X_LATCH, mtr); + bool found; + const page_size_t& page_size + = fil_space_get_page_size(space, &found); + + ut_ad(found); + + node1 = fut_get_ptr(space, page_size, + node1_addr, RW_SX_LATCH, mtr); } flst_write_addr(node1 + FLST_NEXT, fil_addr_null, mtr); @@ -389,7 +443,7 @@ flst_cut_end( flst_write_addr(base + FLST_LAST, node1_addr, mtr); /* Update len of base node */ - len = flst_get_len(base, mtr); + len = flst_get_len(base); ut_ad(len >= n_nodes); mlog_write_ulint(base + FLST_LEN, len - n_nodes, MLOG_4BYTES, mtr); @@ -399,7 +453,6 @@ flst_cut_end( Cuts off the tail of the list, not including the given node. The number of nodes which will be removed must be provided by the caller, as this function does not measure the length of the tail. */ -UNIV_INTERN void flst_truncate_end( /*==============*/ @@ -413,8 +466,12 @@ flst_truncate_end( ulint space; ut_ad(mtr && node2 && base); - ut_ad(mtr_memo_contains_page(mtr, base, MTR_MEMO_PAGE_X_FIX)); - ut_ad(mtr_memo_contains_page(mtr, node2, MTR_MEMO_PAGE_X_FIX)); + ut_ad(mtr_memo_contains_page_flagged(mtr, base, + MTR_MEMO_PAGE_X_FIX + | MTR_MEMO_PAGE_SX_FIX)); + ut_ad(mtr_memo_contains_page_flagged(mtr, node2, + MTR_MEMO_PAGE_X_FIX + | MTR_MEMO_PAGE_SX_FIX)); if (n_nodes == 0) { ut_ad(fil_addr_is_null(flst_get_next_addr(node2, mtr))); @@ -430,7 +487,7 @@ flst_truncate_end( flst_write_addr(base + FLST_LAST, node2_addr, mtr); /* Update len of base node */ - len = flst_get_len(base, mtr); + len = flst_get_len(base); ut_ad(len >= n_nodes); mlog_write_ulint(base + FLST_LEN, len - n_nodes, MLOG_4BYTES, mtr); @@ -438,8 +495,7 @@ flst_truncate_end( /********************************************************************//** Validates a file-based list. -@return TRUE if ok */ -UNIV_INTERN +@return TRUE if ok */ ibool flst_validate( /*==========*/ @@ -447,7 +503,6 @@ flst_validate( mtr_t* mtr1) /*!< in: mtr */ { ulint space; - ulint zip_size; const flst_node_t* node; fil_addr_t node_addr; fil_addr_t base_addr; @@ -456,7 +511,9 @@ flst_validate( mtr_t mtr2; ut_ad(base); - ut_ad(mtr_memo_contains_page(mtr1, base, MTR_MEMO_PAGE_X_FIX)); + ut_ad(mtr_memo_contains_page_flagged(mtr1, base, + MTR_MEMO_PAGE_X_FIX + | MTR_MEMO_PAGE_SX_FIX)); /* We use two mini-transaction handles: the first is used to lock the base node, and prevent other threads from modifying the @@ -467,16 +524,21 @@ flst_validate( /* Find out the space id */ buf_ptr_get_fsp_addr(base, &space, &base_addr); - zip_size = fil_space_get_zip_size(space); - len = flst_get_len(base, mtr1); + bool found; + const page_size_t& page_size = fil_space_get_page_size(space, + &found); + + ut_ad(found); + + len = flst_get_len(base); node_addr = flst_get_first(base, mtr1); for (i = 0; i < len; i++) { mtr_start(&mtr2); - node = fut_get_ptr(space, zip_size, - node_addr, RW_X_LATCH, &mtr2); + node = fut_get_ptr(space, page_size, + node_addr, RW_SX_LATCH, &mtr2); node_addr = flst_get_next_addr(node, &mtr2); mtr_commit(&mtr2); /* Commit mtr2 each round to prevent buffer @@ -490,8 +552,8 @@ flst_validate( for (i = 0; i < len; i++) { mtr_start(&mtr2); - node = fut_get_ptr(space, zip_size, - node_addr, RW_X_LATCH, &mtr2); + node = fut_get_ptr(space, page_size, + node_addr, RW_SX_LATCH, &mtr2); node_addr = flst_get_prev_addr(node, &mtr2); mtr_commit(&mtr2); /* Commit mtr2 each round to prevent buffer @@ -505,7 +567,6 @@ flst_validate( /********************************************************************//** Prints info of a file-based list. */ -UNIV_INTERN void flst_print( /*=======*/ @@ -516,15 +577,16 @@ flst_print( ulint len; ut_ad(base && mtr); - ut_ad(mtr_memo_contains_page(mtr, base, MTR_MEMO_PAGE_X_FIX)); + ut_ad(mtr_memo_contains_page_flagged(mtr, base, + MTR_MEMO_PAGE_X_FIX + | MTR_MEMO_PAGE_SX_FIX)); frame = page_align((byte*) base); - len = flst_get_len(base, mtr); + len = flst_get_len(base); - fprintf(stderr, - "FILE-BASED LIST:\n" - "Base node in space %lu page %lu byte offset %lu; len %lu\n", - (ulong) page_get_space_id(frame), - (ulong) page_get_page_no(frame), - (ulong) page_offset(base), (ulong) len); + ib::info() << "FILE-BASED LIST: Base node in space " + << page_get_space_id(frame) + << "; page " << page_get_page_no(frame) + << "; byte offset " << page_offset(base) + << "; len " << len; } |