/**

  • Latches the leaf page or pages requested. / static void btr_cur_latch_leaves( /=================/ page_t page, /!< in: leaf page where the search converged / ulint space, /!< in: space id / ulint zip_size, /!< in: compressed page size in bytes or 0 for uncompressed pages / ulint page_no, /!< in: page number of the leaf / ulint latch_mode, /!< in: BTR_SEARCH_LEAF, ... / btr_cur_t cursor, /!< in: cursor / mtr_t mtr) /*!< in: mtr / { ulint mode; ulint left_page_no; ulint right_page_no; buf_block_t get_block;

    ut_ad(page && mtr);

    switch (latch_mode) { case BTR_SEARCH_LEAF: case BTR_MODIFY_LEAF: mode = latch_mode == BTR_SEARCH_LEAF ? RW_S_LATCH : RW_X_LATCH; get_block = btr_block_get(space, zip_size, page_no, mode, mtr); #ifdef UNIV_BTR_DEBUG ut_a(page_is_comp(get_block->frame) == page_is_comp(page)); #endif /* UNIV_BTR_DEBUG / get_block->check_index_page_at_flush = TRUE; return; case BTR_MODIFY_TREE: / x-latch also brothers from left to right */ left_page_no = btr_page_get_prev(page, mtr);

     if (left_page_no != FIL_NULL) {
     	get_block = btr_block_get(space, zip_size,
     						  left_page_no,
     						  RW_X_LATCH, mtr);
    

#ifdef UNIV_BTR_DEBUG ut_a(page_is_comp(get_block->frame) == page_is_comp(page)); ut_a(btr_page_get_next(get_block->frame, mtr) == page_get_page_no(page)); #endif /* UNIV_BTR_DEBUG */ get_block->check_index_page_at_flush = TRUE; }

	get_block = btr_block_get(space, zip_size, page_no,
					  RW_X_LATCH, mtr);

#ifdef UNIV_BTR_DEBUG ut_a(page_is_comp(get_block->frame) == page_is_comp(page)); #endif /* UNIV_BTR_DEBUG */ get_block->check_index_page_at_flush = TRUE;

	right_page_no = btr_page_get_next(page, mtr);

	if (right_page_no != FIL_NULL) {
		get_block = btr_block_get(space, zip_size,
						  right_page_no,
						  RW_X_LATCH, mtr);

#ifdef UNIV_BTR_DEBUG ut_a(page_is_comp(get_block->frame) == page_is_comp(page)); ut_a(btr_page_get_prev(get_block->frame, mtr) == page_get_page_no(page)); #endif /* UNIV_BTR_DEBUG */ get_block->check_index_page_at_flush = TRUE; }

	return;

case BTR_SEARCH_PREV:
case BTR_MODIFY_PREV:
	mode = latch_mode == BTR_SEARCH_PREV ? RW_S_LATCH : RW_X_LATCH;
	/* latch also left brother */
	left_page_no = btr_page_get_prev(page, mtr);

	if (left_page_no != FIL_NULL) {
		get_block = btr_block_get(space, zip_size,
						  left_page_no, mode, mtr);
		cursor->left_block = get_block;

#ifdef UNIV_BTR_DEBUG ut_a(page_is_comp(get_block->frame) == page_is_comp(page)); ut_a(btr_page_get_next(get_block->frame, mtr) == page_get_page_no(page)); #endif /* UNIV_BTR_DEBUG */ get_block->check_index_page_at_flush = TRUE; }

	get_block = btr_block_get(space, zip_size, page_no, mode, mtr);

#ifdef UNIV_BTR_DEBUG ut_a(page_is_comp(get_block->frame) == page_is_comp(page)); #endif /* UNIV_BTR_DEBUG */ get_block->check_index_page_at_flush = TRUE; return; }

ut_error;

}

代码分析内容:该函数用于对所需的叶子页进行锁定。

函数参数解析:

  • page:叶子页,搜索结束后的页。
  • space:页所在表空间的ID。
  • zip_size:页的压缩大小(如果未压缩,则为0)。
  • page_no:页号。
  • latch_mode:表示锁定模式(BTR_SEARCH_LEAF,BTR_MODIFY_LEAF,BTR_MODIFY_TREE,BTR_SEARCH_PREV,BTR_MODIFY_PREV)。
  • cursor:游标。
  • mtr:Mini-Transaction。

根据不同的锁定模式,函数的处理方式也不同。

  • BTR_SEARCH_LEAF 和 BTR_MODIFY_LEAF:对叶子页进行S锁或X锁。
  • BTR_MODIFY_TREE:对兄弟页进行X锁,并对叶子页进行X锁。
  • BTR_SEARCH_PREV 和 BTR_MODIFY_PREV:对左兄弟页进行S锁或X锁,并对叶子页进行S锁或X锁。

最后,该函数会设置一个标志,表示在刷新缓冲池时需要检查该页是否是索引页。

Btr Cur Latch Leaves: Locking Leaf Pages in InnoDB

原文地址: https://www.cveoy.top/t/topic/nWVs 著作权归作者所有。请勿转载和采集!

免费AI点我,无需注册和登录