MySQL 8.4.0
Source Code Documentation
page0page.cc File Reference

Index page routines. More...

#include "my_dbug.h"
#include "btr0btr.h"
#include "buf0buf.h"
#include "ibuf0ibuf.h"
#include "page0cur.h"
#include "page0page.h"
#include "page0zip.h"
#include "btr0sea.h"
#include "fut0lst.h"
#include "lock0lock.h"
#include "srv0srv.h"

Functions

ulint page_dir_find_owner_slot (const rec_t *rec)
 Looks for the directory slot which owns the given record. More...
 
static bool page_dir_slot_check (const page_dir_slot_t *slot)
 Used to check the consistency of a directory slot. More...
 
void page_set_max_trx_id (buf_block_t *block, page_zip_des_t *page_zip, trx_id_t trx_id, mtr_t *mtr)
 Sets the max trx id field value. More...
 
bytepage_mem_alloc_heap (page_t *page, page_zip_des_t *page_zip, ulint need, ulint *heap_no)
 Allocates a block of memory from the heap of an index page. More...
 
static void page_create_write_log (buf_frame_t *frame, mtr_t *mtr, bool comp, page_type_t page_type)
 Writes a log record of page creation. More...
 
page_tpage_create_low (buf_block_t *block, ulint comp, page_type_t page_type)
 The index page creation function. More...
 
void page_parse_create (buf_block_t *block, ulint comp, page_type_t page_type)
 Parses a redo log record of creating a page. More...
 
page_tpage_create (buf_block_t *block, mtr_t *mtr, ulint comp, page_type_t page_type)
 Create an uncompressed B-tree or R-tree or SDI index page. More...
 
page_tpage_create_zip (buf_block_t *block, dict_index_t *index, ulint level, trx_id_t max_trx_id, mtr_t *mtr, page_type_t page_type)
 Create a compressed B-tree index page. More...
 
void page_create_empty (buf_block_t *block, dict_index_t *index, mtr_t *mtr)
 Empty a previously created B-tree index page. More...
 
void page_copy_rec_list_end_no_locks (buf_block_t *new_block, buf_block_t *block, rec_t *rec, dict_index_t *index, mtr_t *mtr)
 Differs from page_copy_rec_list_end, because this function does not touch the lock table and max trx id on page or compress the page. More...
 
rec_tpage_copy_rec_list_end (buf_block_t *new_block, buf_block_t *block, rec_t *rec, dict_index_t *index, mtr_t *mtr)
 Copies records from page to new_page, from a given record onward, including that record. More...
 
rec_tpage_copy_rec_list_start (buf_block_t *new_block, buf_block_t *block, rec_t *rec, dict_index_t *index, mtr_t *mtr)
 Copies records from page to new_page, up to the given record, NOT including that record. More...
 
static void page_delete_rec_list_write_log (rec_t *rec, dict_index_t *index, mlog_id_t type, mtr_t *mtr)
 Writes a log record of a record list end or start deletion. More...
 
const bytepage_parse_delete_rec_list (mlog_id_t type, const byte *ptr, const byte *end_ptr, buf_block_t *block, dict_index_t *index, mtr_t *mtr)
 Parses a log record of a record list end or start deletion. More...
 
void page_delete_rec_list_end (rec_t *rec, buf_block_t *block, dict_index_t *index, ulint n_recs, ulint size, mtr_t *mtr)
 Deletes records from a page from a given record onward, including that record. More...
 
void page_delete_rec_list_start (rec_t *rec, buf_block_t *block, dict_index_t *index, mtr_t *mtr)
 Deletes records from page, up to the given record, NOT including that record. More...
 
bool page_move_rec_list_end (buf_block_t *new_block, buf_block_t *block, rec_t *split_rec, dict_index_t *index, mtr_t *mtr)
 Moves record list end to another page. More...
 
bool page_move_rec_list_start (buf_block_t *new_block, buf_block_t *block, rec_t *split_rec, dict_index_t *index, mtr_t *mtr)
 Moves record list start to another page. More...
 
static void page_dir_delete_slot (page_t *page, page_zip_des_t *page_zip, ulint slot_no)
 Used to delete n slots from the directory. More...
 
static void page_dir_add_slot (page_t *page, page_zip_des_t *page_zip, ulint start)
 Used to add n slots to the directory. More...
 
void page_dir_split_slot (page_t *page, page_zip_des_t *page_zip, ulint slot_no)
 Splits a directory slot which owns too many records. More...
 
void page_dir_balance_slot (page_t *page, page_zip_des_t *page_zip, ulint slot_no)
 Tries to balance the given directory slot with too few records with the upper neighbor, so that there are at least the minimum number of records owned by the slot; this may result in the merging of two slots. More...
 
const rec_tpage_rec_get_nth_const (const page_t *page, ulint nth)
 Returns the nth record of the record list. More...
 
ulint page_rec_get_n_recs_before (const rec_t *rec)
 Returns the number of records before the given record in chain. More...
 
void page_rec_print (const rec_t *rec, const ulint *offsets)
 Prints record contents including the data relevant only in the index page context. More...
 
void page_dir_print (page_t *page, ulint pr_n)
 This is used to print the contents of the directory for debugging purposes. More...
 
void page_print_list (buf_block_t *block, dict_index_t *index, ulint pr_n)
 This is used to print the contents of the page record list for debugging purposes. More...
 
void page_header_print (const page_t *page)
 Prints the info in a page header. More...
 
void page_print (buf_block_t *block, dict_index_t *index, ulint dn, ulint rn)
 This is used to print the contents of the page for debugging purposes. More...
 
bool page_rec_validate (const rec_t *rec, const ulint *offsets)
 The following is used to validate a record on a page. More...
 
void page_check_dir (const page_t *page)
 Checks that the first directory slot points to the infimum record and the last to the supremum. More...
 
bool page_simple_validate_old (const page_t *page)
 This function checks the consistency of an index page when we do not know the index. More...
 
bool page_simple_validate_new (const page_t *page)
 This function checks the consistency of an index page when we do not know the index. More...
 
bool page_is_spatial_non_leaf (const rec_t *rec, dict_index_t *index)
 This function checks if the page in which record is present is a non-leaf node of a spatial index. More...
 
bool page_validate (const page_t *page, dict_index_t *index, bool check_min_rec)
 This function checks the consistency of an index page. More...
 
const rec_tpage_find_rec_with_heap_no (const page_t *page, ulint heap_no)
 Looks in the page record list for a record with the given heap number. More...
 
bool page_delete_rec (const dict_index_t *index, page_cur_t *pcur, const ulint *offsets)
 Removes the record from a leaf page. More...
 
const rec_tpage_find_rec_last_not_deleted (const page_t *page)
 Get the last non-delete-marked record on a page. More...
 
void page_warn_strict_checksum (srv_checksum_algorithm_t curr_algo, srv_checksum_algorithm_t page_checksum, const page_id_t &page_id)
 Issue a warning when the checksum that is stored in the page is valid, but different than the global setting innodb_checksum_algorithm. More...
 

Variables

static const byte infimum_supremum_redundant []
 The page infimum and supremum of an empty page in ROW_FORMAT=REDUNDANT. More...
 
static const byte infimum_supremum_compact []
 The page infimum and supremum of an empty page in ROW_FORMAT=COMPACT. More...
 

Detailed Description

Index page routines.

Created 2/2/1994 Heikki Tuuri

Function Documentation

◆ page_check_dir()

void page_check_dir ( const page_t page)

Checks that the first directory slot points to the infimum record and the last to the supremum.

This function is intended to track if the bug fixed in 4.0.14 has caused corruption to users' databases.

Parameters
pagein: index page

◆ page_copy_rec_list_end()

rec_t * page_copy_rec_list_end ( buf_block_t new_block,
buf_block_t block,
rec_t rec,
dict_index_t index,
mtr_t mtr 
)

Copies records from page to new_page, from a given record onward, including that record.

Copies records from page to new_page, from the given record onward, including that record.

Infimum and supremum records are not copied. The records are copied to the start of the record list on new_page.

IMPORTANT: The caller will have to update IBUF_BITMAP_FREE if new_block is a compressed leaf page in a secondary index. This has to be done either within the same mini-transaction, or by invoking ibuf_reset_free_bits() before mtr_commit().

Returns
pointer to the original successor of the infimum record on new_page, or NULL on zip overflow (new_block will be decompressed)
Parameters
new_blockin/out: index page to copy to
blockin: index page containing rec
recin: record on page
indexin: record descriptor
mtrin: mtr

◆ page_copy_rec_list_end_no_locks()

void page_copy_rec_list_end_no_locks ( buf_block_t new_block,
buf_block_t block,
rec_t rec,
dict_index_t index,
mtr_t mtr 
)

Differs from page_copy_rec_list_end, because this function does not touch the lock table and max trx id on page or compress the page.

IMPORTANT: The caller will have to update IBUF_BITMAP_FREE if new_block is a compressed leaf page in a secondary index. This has to be done either within the same mini-transaction, or by invoking ibuf_reset_free_bits() before mtr_commit().

Parameters
new_blockin: index page to copy to
blockin: index page of rec
recin: record on page
indexin: record descriptor
mtrin: mtr

◆ page_copy_rec_list_start()

rec_t * page_copy_rec_list_start ( buf_block_t new_block,
buf_block_t block,
rec_t rec,
dict_index_t index,
mtr_t mtr 
)

Copies records from page to new_page, up to the given record, NOT including that record.

Infimum and supremum records are not copied. The records are copied to the end of the record list on new_page.

IMPORTANT: The caller will have to update IBUF_BITMAP_FREE if new_block is a compressed leaf page in a secondary index. This has to be done either within the same mini-transaction, or by invoking ibuf_reset_free_bits() before mtr_commit().

Returns
pointer to the original predecessor of the supremum record on new_page, or NULL on zip overflow (new_block will be decompressed)
Parameters
new_blockin/out: index page to copy to
blockin: index page containing rec
recin: record on page
indexin: record descriptor
mtrin: mtr

◆ page_create()

page_t * page_create ( buf_block_t block,
mtr_t mtr,
ulint  comp,
page_type_t  page_type 
)

Create an uncompressed B-tree or R-tree or SDI index page.

Parameters
[in]blockA buffer block where the page is created
[in]mtrMini-transaction handle
[in]compnonzero=compact page format
[in]page_typePage type
Returns
pointer to the page

◆ page_create_empty()

void page_create_empty ( buf_block_t block,
dict_index_t index,
mtr_t mtr 
)

Empty a previously created B-tree index page.

Parameters
[in,out]blockB-tree block
[in]indexThe index of the page
[in,out]mtrMini-transaction

◆ page_create_low()

page_t * page_create_low ( buf_block_t block,
ulint  comp,
page_type_t  page_type 
)

The index page creation function.

Parameters
[in,out]blocka buffer block where the page is created
[in]compnonzero=compact page format
[in]page_typepage type
Returns
pointer to the page

◆ page_create_write_log()

static void page_create_write_log ( buf_frame_t frame,
mtr_t mtr,
bool  comp,
page_type_t  page_type 
)
inlinestatic

Writes a log record of page creation.

Parameters
[in]frameA buffer frame where the page is created
[in]mtrMini-transaction handle
[in]comptrue=compact page format
[in]page_typePage type

◆ page_create_zip()

page_t * page_create_zip ( buf_block_t block,
dict_index_t index,
ulint  level,
trx_id_t  max_trx_id,
mtr_t mtr,
page_type_t  page_type 
)

Create a compressed B-tree index page.

Parameters
[in,out]blockBuffer frame where the page is created
[in]indexIndex of the page, or NULL when applying TRUNCATE log record during recovery
[in]levelThe B-tree level of the page
[in]max_trx_idPAGE_MAX_TRX_ID
[in]mtrMini-transaction handle
[in]page_typePage type to be created. Only FIL_PAGE_INDEX, FIL_PAGE_RTREE, FIL_PAGE_SDI allowed
Returns
pointer to the page

◆ page_delete_rec()

bool page_delete_rec ( const dict_index_t index,
page_cur_t pcur,
const ulint offsets 
)

Removes the record from a leaf page.

This function does not log any changes. It is used by the IMPORT tablespace functions.

Returns
true if success, i.e., the page did not become too empty
Parameters
[in]indexThe index that the record belongs to.
[in,out]pcurPage cursor on record to delete.
[in]offsetsOffsets for record.

◆ page_delete_rec_list_end()

void page_delete_rec_list_end ( rec_t rec,
buf_block_t block,
dict_index_t index,
ulint  n_recs,
ulint  size,
mtr_t mtr 
)

Deletes records from a page from a given record onward, including that record.

The infimum and supremum records are not deleted.

Parameters
recin: pointer to record on page
blockin: buffer block of the page
indexin: record descriptor
n_recsin: number of records to delete, or ULINT_UNDEFINED if not known
sizein: the sum of the sizes of the records in the end of the chain to delete, or ULINT_UNDEFINED if not known
mtrin: mtr

◆ page_delete_rec_list_start()

void page_delete_rec_list_start ( rec_t rec,
buf_block_t block,
dict_index_t index,
mtr_t mtr 
)

Deletes records from page, up to the given record, NOT including that record.

Infimum and supremum records are not deleted.

Parameters
recin: record on page
blockin: buffer block of the page
indexin: record descriptor
mtrin: mtr

◆ page_delete_rec_list_write_log()

static void page_delete_rec_list_write_log ( rec_t rec,
dict_index_t index,
mlog_id_t  type,
mtr_t mtr 
)
inlinestatic

Writes a log record of a record list end or start deletion.

Parameters
recin: record on page
indexin: record descriptor
typein: operation type: MLOG_LIST_END_DELETE, ...
mtrin: mtr

◆ page_dir_add_slot()

static void page_dir_add_slot ( page_t page,
page_zip_des_t page_zip,
ulint  start 
)
inlinestatic

Used to add n slots to the directory.

Does not set the record pointers in the added slots or update n_owned values: this is the responsibility of the caller.

Parameters
pagein/out: the index page
page_zipin/out: comprssed page, or NULL
startin: the slot above which the new slots are added

◆ page_dir_balance_slot()

void page_dir_balance_slot ( page_t page,
page_zip_des_t page_zip,
ulint  slot_no 
)

Tries to balance the given directory slot with too few records with the upper neighbor, so that there are at least the minimum number of records owned by the slot; this may result in the merging of two slots.

Parameters
[in,out]pageIndex page
[in,out]page_zipCompressed page, or null
[in]slot_noThe directory slot

◆ page_dir_delete_slot()

static void page_dir_delete_slot ( page_t page,
page_zip_des_t page_zip,
ulint  slot_no 
)
inlinestatic

Used to delete n slots from the directory.

This function updates also n_owned fields in the records, so that the first slot after the deleted ones inherits the records of the deleted slots.

Parameters
pagein/out: the index page
page_zipin/out: compressed page, or NULL
slot_noin: slot to be deleted

◆ page_dir_find_owner_slot()

ulint page_dir_find_owner_slot ( const rec_t rec)

Looks for the directory slot which owns the given record.

Returns
the directory slot number
Parameters
recin: the physical record

◆ page_dir_print()

void page_dir_print ( page_t page,
ulint  pr_n 
)

This is used to print the contents of the directory for debugging purposes.

in: print n first and n last entries

Parameters
pagein: index page
pr_nin: print n first and n last entries

◆ page_dir_slot_check()

static bool page_dir_slot_check ( const page_dir_slot_t slot)
static

Used to check the consistency of a directory slot.

Returns
true if succeed
Parameters
slotin: slot

◆ page_dir_split_slot()

void page_dir_split_slot ( page_t page,
page_zip_des_t page_zip,
ulint  slot_no 
)

Splits a directory slot which owns too many records.

Parameters
[in,out]pageIndex page
[in,out]page_zipCompressed page whose uncompressed part will be written, or null
[in]slot_noThe directory slot

◆ page_find_rec_last_not_deleted()

const rec_t * page_find_rec_last_not_deleted ( const page_t page)

Get the last non-delete-marked record on a page.

Parameters
[in]pageindex tree leaf page
Returns
the last record, not delete-marked
Return values
infimumrecord if all records are delete-marked

◆ page_find_rec_with_heap_no()

const rec_t * page_find_rec_with_heap_no ( const page_t page,
ulint  heap_no 
)

Looks in the page record list for a record with the given heap number.

Returns
record, NULL if not found
Parameters
pagein: index page
heap_noin: heap number

◆ page_header_print()

void page_header_print ( const page_t page)

Prints the info in a page header.

in: index page

◆ page_is_spatial_non_leaf()

bool page_is_spatial_non_leaf ( const rec_t rec,
dict_index_t index 
)

This function checks if the page in which record is present is a non-leaf node of a spatial index.

param[in] rec Btree record param[in] index index

Returns
true if ok

◆ page_mem_alloc_heap()

byte * page_mem_alloc_heap ( page_t page,
page_zip_des_t page_zip,
ulint  need,
ulint heap_no 
)

Allocates a block of memory from the heap of an index page.

Returns
pointer to start of allocated buffer, or NULL if allocation fails
Parameters
pagein/out: index page
page_zipin/out: compressed page with enough space available for inserting the record, or NULL
needin: total number of bytes needed
heap_noout: this contains the heap number of the allocated record if allocation succeeds

◆ page_move_rec_list_end()

bool page_move_rec_list_end ( buf_block_t new_block,
buf_block_t block,
rec_t split_rec,
dict_index_t index,
mtr_t mtr 
)

Moves record list end to another page.

Moved records include split_rec.

IMPORTANT: The caller will have to update IBUF_BITMAP_FREE if new_block is a compressed leaf page in a secondary index. This has to be done either within the same mini-transaction, or by invoking ibuf_reset_free_bits() before mtr_commit().

Returns
true on success; false on compression failure (new_block will be decompressed)
Parameters
new_blockin/out: index page where to move
blockin: index page from where to move
split_recin: first record to move
indexin: record descriptor
mtrin: mtr

◆ page_move_rec_list_start()

bool page_move_rec_list_start ( buf_block_t new_block,
buf_block_t block,
rec_t split_rec,
dict_index_t index,
mtr_t mtr 
)

Moves record list start to another page.

Moved records do not include split_rec.

IMPORTANT: The caller will have to update IBUF_BITMAP_FREE if new_block is a compressed leaf page in a secondary index. This has to be done either within the same mini-transaction, or by invoking ibuf_reset_free_bits() before mtr_commit().

Returns
true on success; false on compression failure
Parameters
new_blockin/out: index page where to move
blockin/out: page containing split_rec
split_recin: first record not to move
indexin: record descriptor
mtrin: mtr

◆ page_parse_create()

void page_parse_create ( buf_block_t block,
ulint  comp,
page_type_t  page_type 
)

Parses a redo log record of creating a page.

Parameters
[in,out]blockbuffer block, or NULL
[in]compnonzero=compact page format
[in]page_typepage type (FIL_PAGE_INDEX, FIL_PAGE_RTREE or FIL_PAGE_SDI)

◆ page_parse_delete_rec_list()

const byte * page_parse_delete_rec_list ( mlog_id_t  type,
const byte ptr,
const byte end_ptr,
buf_block_t block,
dict_index_t index,
mtr_t mtr 
)

Parses a log record of a record list end or start deletion.

Returns
end of log record or NULL
Parameters
typein: MLOG_LIST_END_DELETE, MLOG_LIST_START_DELETE, MLOG_COMP_LIST_END_DELETE or MLOG_COMP_LIST_START_DELETE
ptrin: buffer
end_ptrin: buffer end
blockin/out: buffer block or NULL
indexin: record descriptor
mtrin: mtr or NULL

◆ page_print()

void page_print ( buf_block_t block,
dict_index_t index,
ulint  dn,
ulint  rn 
)

This is used to print the contents of the page for debugging purposes.

in: print rn first and last records in directory

Parameters
blockin: index page
indexin: dictionary index of the page
dnin: print dn first and last entries in directory
rnin: print rn first and last records in directory

◆ page_print_list()

void page_print_list ( buf_block_t block,
dict_index_t index,
ulint  pr_n 
)

This is used to print the contents of the page record list for debugging purposes.

in: print n first and n last entries

Parameters
blockin: index page
indexin: dictionary index of the page
pr_nin: print n first and n last entries

◆ page_rec_get_n_recs_before()

ulint page_rec_get_n_recs_before ( const rec_t rec)

Returns the number of records before the given record in chain.

The number includes infimum and supremum records.

Returns
number of records
Parameters
recin: the physical record

◆ page_rec_get_nth_const()

const rec_t * page_rec_get_nth_const ( const page_t page,
ulint  nth 
)

Returns the nth record of the record list.

This is the inverse function of page_rec_get_n_recs_before().

Returns
nth record
Parameters
pagein: page
nthin: nth record

◆ page_rec_print()

void page_rec_print ( const rec_t rec,
const ulint offsets 
)

Prints record contents including the data relevant only in the index page context.

Parameters
[in]recPhysical record
[in]offsetsRecord descriptor

◆ page_rec_validate()

bool page_rec_validate ( const rec_t rec,
const ulint offsets 
)

The following is used to validate a record on a page.

This function differs from rec_validate as it can also check the n_owned field and the heap_no field.

Returns
true if ok
Parameters
recin: physical record
offsetsin: array returned by rec_get_offsets()

◆ page_set_max_trx_id()

void page_set_max_trx_id ( buf_block_t block,
page_zip_des_t page_zip,
trx_id_t  trx_id,
mtr_t mtr 
)

Sets the max trx id field value.

Parameters
[in,out]blockPage
[in,out]page_zipCompressed page, or NULL
[in]trx_idTransaction id
[in,out]mtrMini-transaction, or NULL

◆ page_simple_validate_new()

bool page_simple_validate_new ( const page_t page)

This function checks the consistency of an index page when we do not know the index.

This is also resilient so that this should never crash even if the page is total garbage.

Returns
true if ok
Parameters
pagein: index page in ROW_FORMAT!=REDUNDANT

◆ page_simple_validate_old()

bool page_simple_validate_old ( const page_t page)

This function checks the consistency of an index page when we do not know the index.

This is also resilient so that this should never crash even if the page is total garbage.

Returns
true if ok
Parameters
pagein: index page in ROW_FORMAT=REDUNDANT

◆ page_validate()

bool page_validate ( const page_t page,
dict_index_t index,
bool  check_min_rec = true 
)

This function checks the consistency of an index page.

Parameters
[in]pageindex page
[in]indexdata dictionary index containing the page record type definition
[in]check_min_reccheck whether min rec flag (REC_INFO_MIN_REC_FLAG) is correctly set in the page. The default value is true.
Returns
true if ok

◆ page_warn_strict_checksum()

void page_warn_strict_checksum ( srv_checksum_algorithm_t  curr_algo,
srv_checksum_algorithm_t  page_checksum,
const page_id_t page_id 
)

Issue a warning when the checksum that is stored in the page is valid, but different than the global setting innodb_checksum_algorithm.

Parameters
[in]curr_algocurrent checksum algorithm
[in]page_checksumpage valid checksum
[in]page_idpage identifier

Variable Documentation

◆ infimum_supremum_compact

const byte infimum_supremum_compact[]
static
Initial value:
= {
0x01 , 0x00, 0x02 , 0x00,
0x0d , 'i', 'n', 'f', 'i', 'm', 'u', 'm', 0,
0x01 , 0x00, 0x0b , 0x00,
0x00 , 's', 'u', 'p', 'r', 'e', 'm', 'u', 'm'}

The page infimum and supremum of an empty page in ROW_FORMAT=COMPACT.

◆ infimum_supremum_redundant

const byte infimum_supremum_redundant[]
static
Initial value:
= {
0x08 , 0x01 , 0x00, 0x00 ,
0x03 , 0x00, 0x74 ,
'i', 'n', 'f', 'i', 'm', 'u', 'm', 0,
0x09 , 0x01 , 0x00, 0x08 ,
0x03 , 0x00, 0x00 ,
's', 'u', 'p', 'r', 'e', 'm', 'u', 'm', 0}

The page infimum and supremum of an empty page in ROW_FORMAT=REDUNDANT.