1/*****************************************************************************
2
3Copyright (c) 1996, 2015, Oracle and/or its affiliates. All Rights Reserved.
4Copyright (c) 2017, 2018, MariaDB Corporation.
5
6This program is free software; you can redistribute it and/or modify it under
7the terms of the GNU General Public License as published by the Free Software
8Foundation; version 2 of the License.
9
10This program is distributed in the hope that it will be useful, but WITHOUT
11ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
12FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details.
13
14You should have received a copy of the GNU General Public License along with
15this program; if not, write to the Free Software Foundation, Inc.,
1651 Franklin Street, Fifth Floor, Boston, MA 02110-1335 USA
17
18*****************************************************************************/
19
20/**************************************************//**
21@file include/lock0lock.ic
22The transaction lock system
23
24Created 5/7/1996 Heikki Tuuri
25*******************************************************/
26
27#include "dict0dict.h"
28#include "buf0buf.h"
29#include "page0page.h"
30
31/*********************************************************************//**
32Calculates the fold value of a page file address: used in inserting or
33searching for a lock in the hash table.
34@return folded value */
35UNIV_INLINE
36ulint
37lock_rec_fold(
38/*==========*/
39	ulint	space,	/*!< in: space */
40	ulint	page_no)/*!< in: page number */
41{
42	return(ut_fold_ulint_pair(space, page_no));
43}
44
45/*********************************************************************//**
46Calculates the hash value of a page file address: used in inserting or
47searching for a lock in the hash table.
48@return hashed value */
49UNIV_INLINE
50unsigned
51lock_rec_hash(
52/*==========*/
53	ulint	space,	/*!< in: space */
54	ulint	page_no)/*!< in: page number */
55{
56	return(unsigned(hash_calc_hash(lock_rec_fold(space, page_no),
57				       lock_sys.rec_hash)));
58}
59
60/*********************************************************************//**
61Gets the heap_no of the smallest user record on a page.
62@return heap_no of smallest user record, or PAGE_HEAP_NO_SUPREMUM */
63UNIV_INLINE
64ulint
65lock_get_min_heap_no(
66/*=================*/
67	const buf_block_t*	block)	/*!< in: buffer block */
68{
69	const page_t*	page	= block->frame;
70
71	if (page_is_comp(page)) {
72		return(rec_get_heap_no_new(
73			       page
74			       + rec_get_next_offs(page + PAGE_NEW_INFIMUM,
75						   TRUE)));
76	} else {
77		return(rec_get_heap_no_old(
78			       page
79			       + rec_get_next_offs(page + PAGE_OLD_INFIMUM,
80						   FALSE)));
81	}
82}
83
84/*************************************************************//**
85Get the lock hash table */
86UNIV_INLINE
87hash_table_t*
88lock_hash_get(
89/*==========*/
90	ulint	mode)	/*!< in: lock mode */
91{
92	if (mode & LOCK_PREDICATE) {
93		return(lock_sys.prdt_hash);
94	} else if (mode & LOCK_PRDT_PAGE) {
95		return(lock_sys.prdt_page_hash);
96	} else {
97		return(lock_sys.rec_hash);
98	}
99}
100
101/*********************************************************************//**
102Creates a new record lock and inserts it to the lock queue. Does NOT check
103for deadlocks or lock compatibility!
104@return created lock */
105UNIV_INLINE
106lock_t*
107lock_rec_create(
108/*============*/
109#ifdef WITH_WSREP
110	lock_t*			c_lock,	/*!< conflicting lock */
111	que_thr_t*		thr,	/*!< thread owning trx */
112#endif
113	ulint			type_mode,/*!< in: lock mode and wait
114					flag, type is ignored and
115					replaced by LOCK_REC */
116	const buf_block_t*	block,	/*!< in: buffer block containing
117					the record */
118	ulint			heap_no,/*!< in: heap number of the record */
119	dict_index_t*		index,	/*!< in: index of record */
120	trx_t*			trx,	/*!< in,out: transaction */
121	bool			caller_owns_trx_mutex)
122					/*!< in: TRUE if caller owns
123					trx mutex */
124{
125	btr_assert_not_corrupted(block, index);
126	return lock_rec_create_low(
127#ifdef WITH_WSREP
128		c_lock, thr,
129#endif
130		type_mode,
131		block->page.id.space(), block->page.id.page_no(),
132		block->frame, heap_no,
133		index, trx, caller_owns_trx_mutex);
134}
135