📄 page0page.ic
字号:
/******************************************************Index page routines(c) 1994-1996 Innobase OyCreated 2/2/1994 Heikki Tuuri*******************************************************/#include "mach0data.h"#include "rem0cmp.h"#include "mtr0log.h"#ifdef UNIV_MATERIALIZE#undef UNIV_INLINE#define UNIV_INLINE#endif/*****************************************************************Returns the max trx id field value. */UNIV_INLINEdulintpage_get_max_trx_id(/*================*/ page_t* page) /* in: page */{ ut_ad(page); return(mach_read_from_8(page + PAGE_HEADER + PAGE_MAX_TRX_ID));}/*****************************************************************Sets the max trx id field value if trx_id is bigger than the previousvalue. */UNIV_INLINEvoidpage_update_max_trx_id(/*===================*/ page_t* page, /* in: page */ dulint trx_id) /* in: transaction id */{ ut_ad(page); if (ut_dulint_cmp(page_get_max_trx_id(page), trx_id) < 0) { page_set_max_trx_id(page, trx_id); }}/*****************************************************************Reads the given header field. */UNIV_INLINEulintpage_header_get_field(/*==================*/ page_t* page, /* in: page */ ulint field) /* in: PAGE_LEVEL, ... */{ ut_ad(page); ut_ad(field <= PAGE_INDEX_ID); return(mach_read_from_2(page + PAGE_HEADER + field));}/*****************************************************************Sets the given header field. */UNIV_INLINEvoidpage_header_set_field(/*==================*/ page_t* page, /* in: page */ ulint field, /* in: PAGE_LEVEL, ... */ ulint val) /* in: value */{ ut_ad(page); ut_ad(field <= PAGE_N_RECS); ut_ad(field == PAGE_N_HEAP || val < UNIV_PAGE_SIZE); ut_ad(field != PAGE_N_HEAP || (val & 0x7fff) < UNIV_PAGE_SIZE); mach_write_to_2(page + PAGE_HEADER + field, val);}/*****************************************************************Returns the pointer stored in the given header field. */UNIV_INLINEbyte*page_header_get_ptr(/*================*/ /* out: pointer or NULL */ page_t* page, /* in: page */ ulint field) /* in: PAGE_FREE, ... */{ ulint offs; ut_ad(page); ut_ad((field == PAGE_FREE) || (field == PAGE_LAST_INSERT) || (field == PAGE_HEAP_TOP)); offs = page_header_get_field(page, field); ut_ad((field != PAGE_HEAP_TOP) || offs); if (offs == 0) { return(NULL); } return(page + offs);}/*****************************************************************Sets the pointer stored in the given header field. */UNIV_INLINEvoidpage_header_set_ptr(/*================*/ page_t* page, /* in: page */ ulint field, /* in: PAGE_FREE, ... */ byte* ptr) /* in: pointer or NULL*/{ ulint offs; ut_ad(page); ut_ad((field == PAGE_FREE) || (field == PAGE_LAST_INSERT) || (field == PAGE_HEAP_TOP)); if (ptr == NULL) { offs = 0; } else { offs = ptr - page; } ut_ad((field != PAGE_HEAP_TOP) || offs); page_header_set_field(page, field, offs);}/*****************************************************************Resets the last insert info field in the page header. Writes to mlogabout this operation. */UNIV_INLINEvoidpage_header_reset_last_insert(/*==========================*/ page_t* page, /* in: page */ mtr_t* mtr) /* in: mtr */{ ut_ad(page && mtr); mlog_write_ulint(page + PAGE_HEADER + PAGE_LAST_INSERT, 0, MLOG_2BYTES, mtr);}/****************************************************************Determine whether the page is in new-style compact format. */UNIV_INLINEulintpage_is_comp(/*=========*/ /* out: nonzero if the page is in compact format, zero if it is in old-style format */ 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_INLINEulintpage_rec_is_comp(/*=============*/ /* out: nonzero if in compact format */ const rec_t* rec) /* in: record */{ return(page_is_comp(ut_align_down((rec_t*) rec, UNIV_PAGE_SIZE)));}/****************************************************************Gets the first record on the page. */UNIV_INLINErec_t*page_get_infimum_rec(/*=================*/ /* out: the first record in record list */ page_t* page) /* in: page which must have record(s) */{ ut_ad(page); if (page_is_comp(page)) { return(page + PAGE_NEW_INFIMUM); } else { return(page + PAGE_OLD_INFIMUM); }}/****************************************************************Gets the last record on the page. */UNIV_INLINErec_t*page_get_supremum_rec(/*==================*/ /* out: the last record in record list */ page_t* page) /* in: page which must have record(s) */{ ut_ad(page); if (page_is_comp(page)) { return(page + PAGE_NEW_SUPREMUM); } else { return(page + PAGE_OLD_SUPREMUM); }}/****************************************************************TRUE if the record is a user record on the page. */UNIV_INLINEiboolpage_rec_is_user_rec_low(/*=====================*/ /* out: TRUE if a user record */ ulint offset) /* in: record offset on page */{ ut_ad(offset >= PAGE_NEW_INFIMUM);#if PAGE_OLD_INFIMUM < PAGE_NEW_INFIMUM# error "PAGE_OLD_INFIMUM < PAGE_NEW_INFIMUM"#endif#if PAGE_OLD_SUPREMUM < PAGE_NEW_SUPREMUM# error "PAGE_OLD_SUPREMUM < PAGE_NEW_SUPREMUM"#endif#if PAGE_NEW_INFIMUM > PAGE_OLD_SUPREMUM# error "PAGE_NEW_INFIMUM > PAGE_OLD_SUPREMUM"#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(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. */UNIV_INLINEiboolpage_rec_is_supremum_low(/*=====================*/ /* out: TRUE if the supremum record */ ulint offset) /* in: record offset on page */{ ut_ad(offset >= PAGE_NEW_INFIMUM); ut_ad(offset <= UNIV_PAGE_SIZE - PAGE_EMPTY_DIR_START); return(UNIV_UNLIKELY(offset == PAGE_NEW_SUPREMUM) || UNIV_UNLIKELY(offset == PAGE_OLD_SUPREMUM));}/****************************************************************TRUE if the record is the infimum record on a page. */UNIV_INLINEiboolpage_rec_is_infimum_low(/*=====================*/ /* out: TRUE if the infimum record */ ulint offset) /* in: record offset on page */{ ut_ad(offset >= PAGE_NEW_INFIMUM); ut_ad(offset <= UNIV_PAGE_SIZE - PAGE_EMPTY_DIR_START); return(UNIV_UNLIKELY(offset == PAGE_NEW_INFIMUM) || UNIV_UNLIKELY(offset == PAGE_OLD_INFIMUM));}/****************************************************************TRUE if the record is a user record on the page. */UNIV_INLINEiboolpage_rec_is_user_rec(/*=================*/ /* out: TRUE if a user record */ const rec_t* rec) /* in: record */{ return(page_rec_is_user_rec_low( ut_align_offset(rec, UNIV_PAGE_SIZE)));}/****************************************************************TRUE if the record is the supremum record on a page. */UNIV_INLINEiboolpage_rec_is_supremum(/*=================*/ /* out: TRUE if the supremum record */ const rec_t* rec) /* in: record */{ return(page_rec_is_supremum_low( ut_align_offset(rec, UNIV_PAGE_SIZE)));}/****************************************************************TRUE if the record is the infimum record on a page. */UNIV_INLINEiboolpage_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)));}/*****************************************************************Compares a data tuple to a physical record. Differs from the functioncmp_dtuple_rec_with_match in the way that the record must reside on anindex page, and also page infimum and supremum records can be given inthe parameter rec. These are considered as the negative infinity andthe positive infinity in the alphabetical order. */UNIV_INLINEintpage_cmp_dtuple_rec_with_match(/*===========================*/ /* out: 1, 0, -1, if dtuple is greater, equal, less than rec, respectively, when only the common first fields are compared */ dtuple_t* dtuple, /* in: data tuple */ rec_t* rec, /* in: physical record on a page; may also be page infimum or supremum, in which case matched-parameter values below are not affected */ const ulint* offsets,/* in: array returned by rec_get_offsets() */ ulint* matched_fields, /* in/out: number of already completely matched fields; when function returns contains the value for current comparison */ ulint* matched_bytes) /* in/out: number of already matched bytes within the first field not completely matched; when function returns contains the value for current comparison */{ ulint rec_offset; ut_ad(dtuple_check_typed(dtuple)); ut_ad(rec_offs_validate(rec, NULL, offsets)); ut_ad(!rec_offs_comp(offsets) == !page_rec_is_comp(rec)); rec_offset = ut_align_offset(rec, UNIV_PAGE_SIZE); if (UNIV_UNLIKELY(rec_offset == PAGE_NEW_INFIMUM) || UNIV_UNLIKELY(rec_offset == PAGE_OLD_INFIMUM)) { return(1); } if (UNIV_UNLIKELY(rec_offset == PAGE_NEW_SUPREMUM) || UNIV_UNLIKELY(rec_offset == PAGE_OLD_SUPREMUM)) { return(-1); } return(cmp_dtuple_rec_with_match(dtuple, rec, offsets, matched_fields, matched_bytes));}/*****************************************************************Gets the number of user records on page (infimum and supremum recordsare not user records). */UNIV_INLINEulintpage_get_n_recs(/*============*/ /* out: number of user records */ page_t* page) /* in: index page */{ return(page_header_get_field(page, PAGE_N_RECS));}/*****************************************************************Gets the number of dir slots in directory. */UNIV_INLINEulintpage_dir_get_n_slots(/*=================*/ /* out: number of slots */ page_t* page) /* in: index page */{ return(page_header_get_field(page, PAGE_N_DIR_SLOTS));}/*****************************************************************Sets the number of dir slots in directory. */UNIV_INLINEvoidpage_dir_set_n_slots(/*=================*/ /* out: number of slots */ page_t* page, /* in: index page */ ulint n_slots)/* in: number of slots */{ page_header_set_field(page, PAGE_N_DIR_SLOTS, n_slots);}/*****************************************************************Gets the number of records in the heap. */UNIV_INLINEulintpage_dir_get_n_heap(/*================*/
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -