trx0undo.h 20.4 KB
Newer Older
Vadim Tkachenko's avatar
Vadim Tkachenko committed
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18
/*****************************************************************************

Copyright (c) 1996, 2009, Innobase Oy. 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
Foundation; version 2 of the License.

This program is distributed in the hope that it will be useful, but WITHOUT
ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details.

You should have received a copy of the GNU General Public License along with
this program; if not, write to the Free Software Foundation, Inc., 59 Temple
Place, Suite 330, Boston, MA 02111-1307 USA

*****************************************************************************/

19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 222 223 224 225 226 227 228 229 230 231 232 233 234 235 236 237 238 239 240 241 242 243 244 245 246 247 248 249 250
/******************************************************
Transaction undo log

Created 3/26/1996 Heikki Tuuri
*******************************************************/

#ifndef trx0undo_h
#define trx0undo_h

#include "univ.i"
#include "trx0types.h"
#include "mtr0mtr.h"
#include "trx0sys.h"
#include "page0types.h"
#include "trx0xa.h"

/***************************************************************************
Builds a roll pointer dulint. */
UNIV_INLINE
dulint
trx_undo_build_roll_ptr(
/*====================*/
				/* out: roll pointer */
	ibool	is_insert,	/* in: TRUE if insert undo log */
	ulint	rseg_id,	/* in: rollback segment id */
	ulint	page_no,	/* in: page number */
	ulint	offset);	/* in: offset of the undo entry within page */
/***************************************************************************
Decodes a roll pointer dulint. */
UNIV_INLINE
void
trx_undo_decode_roll_ptr(
/*=====================*/
	dulint	roll_ptr,	/* in: roll pointer */
	ibool*	is_insert,	/* out: TRUE if insert undo log */
	ulint*	rseg_id,	/* out: rollback segment id */
	ulint*	page_no,	/* out: page number */
	ulint*	offset);	/* out: offset of the undo entry within page */
/***************************************************************************
Returns TRUE if the roll pointer is of the insert type. */
UNIV_INLINE
ibool
trx_undo_roll_ptr_is_insert(
/*========================*/
				/* out: TRUE if insert undo log */
	dulint	roll_ptr);	/* in: roll pointer */
/*********************************************************************
Writes a roll ptr to an index page. In case that the size changes in
some future version, this function should be used instead of
mach_write_... */
UNIV_INLINE
void
trx_write_roll_ptr(
/*===============*/
	byte*	ptr,		/* in: pointer to memory where written */
	dulint	roll_ptr);	/* in: roll ptr */
/*********************************************************************
Reads a roll ptr from an index page. In case that the roll ptr size
changes in some future version, this function should be used instead of
mach_read_... */
UNIV_INLINE
dulint
trx_read_roll_ptr(
/*==============*/
				/* out: roll ptr */
	const byte*	ptr);	/* in: pointer to memory from where to read */
/**********************************************************************
Gets an undo log page and x-latches it. */
UNIV_INLINE
page_t*
trx_undo_page_get(
/*==============*/
				/* out: pointer to page x-latched */
	ulint	space,		/* in: space where placed */
	ulint	zip_size,	/* in: compressed page size in bytes
				or 0 for uncompressed pages */
	ulint	page_no,	/* in: page number */
	mtr_t*	mtr);		/* in: mtr */
/**********************************************************************
Gets an undo log page and s-latches it. */
UNIV_INLINE
page_t*
trx_undo_page_get_s_latched(
/*========================*/
				/* out: pointer to page s-latched */
	ulint	space,		/* in: space where placed */
	ulint	zip_size,	/* in: compressed page size in bytes
				or 0 for uncompressed pages */
	ulint	page_no,	/* in: page number */
	mtr_t*	mtr);		/* in: mtr */
/**********************************************************************
Returns the previous undo record on the page in the specified log, or
NULL if none exists. */
UNIV_INLINE
trx_undo_rec_t*
trx_undo_page_get_prev_rec(
/*=======================*/
				/* out: pointer to record, NULL if none */
	trx_undo_rec_t*	rec,	/* in: undo log record */
	ulint		page_no,/* in: undo log header page number */
	ulint		offset);/* in: undo log header offset on page */
/**********************************************************************
Returns the next undo log record on the page in the specified log, or
NULL if none exists. */
UNIV_INLINE
trx_undo_rec_t*
trx_undo_page_get_next_rec(
/*=======================*/
				/* out: pointer to record, NULL if none */
	trx_undo_rec_t*	rec,	/* in: undo log record */
	ulint		page_no,/* in: undo log header page number */
	ulint		offset);/* in: undo log header offset on page */
/**********************************************************************
Returns the last undo record on the page in the specified undo log, or
NULL if none exists. */
UNIV_INLINE
trx_undo_rec_t*
trx_undo_page_get_last_rec(
/*=======================*/
			/* out: pointer to record, NULL if none */
	page_t*	undo_page,/* in: undo log page */
	ulint	page_no,/* in: undo log header page number */
	ulint	offset);	/* in: undo log header offset on page */
/**********************************************************************
Returns the first undo record on the page in the specified undo log, or
NULL if none exists. */
UNIV_INLINE
trx_undo_rec_t*
trx_undo_page_get_first_rec(
/*========================*/
			/* out: pointer to record, NULL if none */
	page_t*	undo_page,/* in: undo log page */
	ulint	page_no,/* in: undo log header page number */
	ulint	offset);/* in: undo log header offset on page */
/***************************************************************************
Gets the previous record in an undo log. */
UNIV_INTERN
trx_undo_rec_t*
trx_undo_get_prev_rec(
/*==================*/
				/* out: undo log record, the page s-latched,
				NULL if none */
	trx_undo_rec_t*	rec,	/* in: undo record */
	ulint		page_no,/* in: undo log header page number */
	ulint		offset,	/* in: undo log header offset on page */
	mtr_t*		mtr);	/* in: mtr */
/***************************************************************************
Gets the next record in an undo log. */
UNIV_INTERN
trx_undo_rec_t*
trx_undo_get_next_rec(
/*==================*/
				/* out: undo log record, the page s-latched,
				NULL if none */
	trx_undo_rec_t*	rec,	/* in: undo record */
	ulint		page_no,/* in: undo log header page number */
	ulint		offset,	/* in: undo log header offset on page */
	mtr_t*		mtr);	/* in: mtr */
/***************************************************************************
Gets the first record in an undo log. */
UNIV_INTERN
trx_undo_rec_t*
trx_undo_get_first_rec(
/*===================*/
			/* out: undo log record, the page latched, NULL if
			none */
	ulint	space,	/* in: undo log header space */
	ulint	zip_size,/* in: compressed page size in bytes
			or 0 for uncompressed pages */
	ulint	page_no,/* in: undo log header page number */
	ulint	offset,	/* in: undo log header offset on page */
	ulint	mode,	/* in: latching mode: RW_S_LATCH or RW_X_LATCH */
	mtr_t*	mtr);	/* in: mtr */
/************************************************************************
Tries to add a page to the undo log segment where the undo log is placed. */
UNIV_INTERN
ulint
trx_undo_add_page(
/*==============*/
				/* out: page number if success, else
				FIL_NULL */
	trx_t*		trx,	/* in: transaction */
	trx_undo_t*	undo,	/* in: undo log memory object */
	mtr_t*		mtr);	/* in: mtr which does not have a latch to any
				undo log page; the caller must have reserved
				the rollback segment mutex */
/***************************************************************************
Truncates an undo log from the end. This function is used during a rollback
to free space from an undo log. */
UNIV_INTERN
void
trx_undo_truncate_end(
/*==================*/
	trx_t*		trx,	/* in: transaction whose undo log it is */
	trx_undo_t*	undo,	/* in: undo log */
	dulint		limit);	/* in: all undo records with undo number
				>= this value should be truncated */
/***************************************************************************
Truncates an undo log from the start. This function is used during a purge
operation. */
UNIV_INTERN
void
trx_undo_truncate_start(
/*====================*/
	trx_rseg_t* rseg,	/* in: rollback segment */
	ulint	space,		/* in: space id of the log */
	ulint	hdr_page_no,	/* in: header page number */
	ulint	hdr_offset,	/* in: header offset on the page */
	dulint	limit);		/* in: all undo pages with undo numbers <
				this value should be truncated; NOTE that
				the function only frees whole pages; the
				header page is not freed, but emptied, if
				all the records there are < limit */
/************************************************************************
Initializes the undo log lists for a rollback segment memory copy.
This function is only called when the database is started or a new
rollback segment created. */
UNIV_INTERN
ulint
trx_undo_lists_init(
/*================*/
				/* out: the combined size of undo log segments
				in pages */
	trx_rseg_t*	rseg);	/* in: rollback segment memory object */
/**************************************************************************
Assigns an undo log for a transaction. A new undo log is created or a cached
undo log reused. */
UNIV_INTERN
ulint
trx_undo_assign_undo(
/*=================*/
				/* out: DB_SUCCESS if undo log assign
Vadim Tkachenko's avatar
Vadim Tkachenko committed
251 252 253
				successful, possible error codes are:
				DB_TOO_MANY_CONCURRENT_TRXS
				DB_OUT_OF_FILE_SPACE DB_OUT_OF_MEMORY*/
254 255 256 257 258 259 260 261 262 263 264 265 266 267 268 269 270 271 272 273 274 275 276 277 278 279 280 281 282 283 284 285 286 287 288 289 290 291 292 293 294 295 296 297 298 299 300 301 302 303 304 305 306 307 308 309 310 311 312 313 314 315 316 317 318 319 320 321 322 323 324 325 326 327 328 329 330 331 332 333 334 335 336 337 338 339 340 341 342 343 344 345 346 347 348 349 350 351 352 353 354 355 356 357 358 359 360 361 362 363 364 365 366 367 368 369 370 371 372 373 374 375 376 377 378 379 380 381 382 383 384 385 386 387 388 389 390 391 392 393 394 395 396 397 398 399 400 401 402 403 404 405 406 407 408 409 410 411 412 413 414 415 416 417 418 419 420 421 422 423 424 425 426 427 428 429 430 431 432 433 434 435 436 437 438 439 440 441 442 443 444 445 446 447 448 449 450 451 452 453 454 455 456 457 458 459 460 461 462 463 464 465 466 467 468 469 470 471 472 473 474 475 476 477 478 479 480 481 482 483 484 485 486 487 488 489 490 491 492 493 494 495 496 497 498 499 500 501 502 503 504 505 506 507 508 509 510 511 512 513 514 515 516 517 518 519 520 521 522 523 524 525 526
	trx_t*		trx,	/* in: transaction */
	ulint		type);	/* in: TRX_UNDO_INSERT or TRX_UNDO_UPDATE */
/**********************************************************************
Sets the state of the undo log segment at a transaction finish. */
UNIV_INTERN
page_t*
trx_undo_set_state_at_finish(
/*=========================*/
				/* out: undo log segment header page,
				x-latched */
	trx_rseg_t*	rseg,	/* in: rollback segment memory object */
	trx_t*		trx,	/* in: transaction */
	trx_undo_t*	undo,	/* in: undo log memory copy */
	mtr_t*		mtr);	/* in: mtr */
/**********************************************************************
Sets the state of the undo log segment at a transaction prepare. */
UNIV_INTERN
page_t*
trx_undo_set_state_at_prepare(
/*==========================*/
				/* out: undo log segment header page,
				x-latched */
	trx_t*		trx,	/* in: transaction */
	trx_undo_t*	undo,	/* in: undo log memory copy */
	mtr_t*		mtr);	/* in: mtr */

/**************************************************************************
Adds the update undo log header as the first in the history list, and
frees the memory object, or puts it to the list of cached update undo log
segments. */
UNIV_INTERN
void
trx_undo_update_cleanup(
/*====================*/
	trx_t*	trx,		/* in: trx owning the update undo log */
	page_t*	undo_page,	/* in: update undo log header page,
				x-latched */
	mtr_t*	mtr);		/* in: mtr */
/**********************************************************************
Frees or caches an insert undo log after a transaction commit or rollback.
Knowledge of inserts is not needed after a commit or rollback, therefore
the data can be discarded. */
UNIV_INTERN
void
trx_undo_insert_cleanup(
/*====================*/
	trx_t*	trx);	/* in: transaction handle */
/***************************************************************
Parses the redo log entry of an undo log page initialization. */
UNIV_INTERN
byte*
trx_undo_parse_page_init(
/*=====================*/
			/* out: end of log record or NULL */
	byte*	ptr,	/* in: buffer */
	byte*	end_ptr,/* in: buffer end */
	page_t*	page,	/* in: page or NULL */
	mtr_t*	mtr);	/* in: mtr or NULL */
/***************************************************************
Parses the redo log entry of an undo log page header create or reuse. */
UNIV_INTERN
byte*
trx_undo_parse_page_header(
/*=======================*/
			/* out: end of log record or NULL */
	ulint	type,	/* in: MLOG_UNDO_HDR_CREATE or MLOG_UNDO_HDR_REUSE */
	byte*	ptr,	/* in: buffer */
	byte*	end_ptr,/* in: buffer end */
	page_t*	page,	/* in: page or NULL */
	mtr_t*	mtr);	/* in: mtr or NULL */
/***************************************************************
Parses the redo log entry of an undo log page header discard. */
UNIV_INTERN
byte*
trx_undo_parse_discard_latest(
/*==========================*/
			/* out: end of log record or NULL */
	byte*	ptr,	/* in: buffer */
	byte*	end_ptr,/* in: buffer end */
	page_t*	page,	/* in: page or NULL */
	mtr_t*	mtr);	/* in: mtr or NULL */

/* Types of an undo log segment */
#define	TRX_UNDO_INSERT		1	/* contains undo entries for inserts */
#define	TRX_UNDO_UPDATE		2	/* contains undo entries for updates
					and delete markings: in short,
					modifys (the name 'UPDATE' is a
					historical relic) */
/* States of an undo log segment */
#define TRX_UNDO_ACTIVE		1	/* contains an undo log of an active
					transaction */
#define	TRX_UNDO_CACHED		2	/* cached for quick reuse */
#define	TRX_UNDO_TO_FREE	3	/* insert undo segment can be freed */
#define	TRX_UNDO_TO_PURGE	4	/* update undo segment will not be
					reused: it can be freed in purge when
					all undo data in it is removed */
#define	TRX_UNDO_PREPARED	5	/* contains an undo log of an
					prepared transaction */

/* Transaction undo log memory object; this is protected by the undo_mutex
in the corresponding transaction object */

struct trx_undo_struct{
	/*-----------------------------*/
	ulint		id;		/* undo log slot number within the
					rollback segment */
	ulint		type;		/* TRX_UNDO_INSERT or
					TRX_UNDO_UPDATE */
	ulint		state;		/* state of the corresponding undo log
					segment */
	ibool		del_marks;	/* relevant only in an update undo log:
					this is TRUE if the transaction may
					have delete marked records, because of
					a delete of a row or an update of an
					indexed field; purge is then
					necessary; also TRUE if the transaction
					has updated an externally stored
					field */
	dulint		trx_id;		/* id of the trx assigned to the undo
					log */
	XID		xid;		/* X/Open XA transaction
					identification */
	ibool		dict_operation;	/* TRUE if a dict operation trx */
	dulint		table_id;	/* if a dict operation, then the table
					id */
	trx_rseg_t*	rseg;		/* rseg where the undo log belongs */
	/*-----------------------------*/
	ulint		space;		/* space id where the undo log
					placed */
	ulint		zip_size;	/* in: compressed page size of space
					in bytes, or 0 for uncompressed */
	ulint		hdr_page_no;	/* page number of the header page in
					the undo log */
	ulint		hdr_offset;	/* header offset of the undo log on the
					page */
	ulint		last_page_no;	/* page number of the last page in the
					undo log; this may differ from
					top_page_no during a rollback */
	ulint		size;		/* current size in pages */
	/*-----------------------------*/
	ulint		empty;		/* TRUE if the stack of undo log
					records is currently empty */
	ulint		top_page_no;	/* page number where the latest undo
					log record was catenated; during
					rollback the page from which the latest
					undo record was chosen */
	ulint		top_offset;	/* offset of the latest undo record,
					i.e., the topmost element in the undo
					log if we think of it as a stack */
	dulint		top_undo_no;	/* undo number of the latest record */
	buf_block_t*	guess_block;	/* guess for the buffer block where
					the top page might reside */
	/*-----------------------------*/
	UT_LIST_NODE_T(trx_undo_t) undo_list;
					/* undo log objects in the rollback
					segment are chained into lists */
};

/* The offset of the undo log page header on pages of the undo log */
#define	TRX_UNDO_PAGE_HDR	FSEG_PAGE_DATA
/*-------------------------------------------------------------*/
/* Transaction undo log page header offsets */
#define	TRX_UNDO_PAGE_TYPE	0	/* TRX_UNDO_INSERT or
					TRX_UNDO_UPDATE */
#define	TRX_UNDO_PAGE_START	2	/* Byte offset where the undo log
					records for the LATEST transaction
					start on this page (remember that
					in an update undo log, the first page
					can contain several undo logs) */
#define	TRX_UNDO_PAGE_FREE	4	/* On each page of the undo log this
					field contains the byte offset of the
					first free byte on the page */
#define TRX_UNDO_PAGE_NODE	6	/* The file list node in the chain
					of undo log pages */
/*-------------------------------------------------------------*/
#define TRX_UNDO_PAGE_HDR_SIZE	(6 + FLST_NODE_SIZE)

/* An update undo segment with just one page can be reused if it has
< this number bytes used; we must leave space at least for one new undo
log header on the page */

#define TRX_UNDO_PAGE_REUSE_LIMIT	(3 * UNIV_PAGE_SIZE / 4)

/* An update undo log segment may contain several undo logs on its first page
if the undo logs took so little space that the segment could be cached and
reused. All the undo log headers are then on the first page, and the last one
owns the undo log records on subsequent pages if the segment is bigger than
one page. If an undo log is stored in a segment, then on the first page it is
allowed to have zero undo records, but if the segment extends to several
pages, then all the rest of the pages must contain at least one undo log
record. */

/* The offset of the undo log segment header on the first page of the undo
log segment */

#define	TRX_UNDO_SEG_HDR	(TRX_UNDO_PAGE_HDR + TRX_UNDO_PAGE_HDR_SIZE)
/*-------------------------------------------------------------*/
#define	TRX_UNDO_STATE		0	/* TRX_UNDO_ACTIVE, ... */
#define	TRX_UNDO_LAST_LOG	2	/* Offset of the last undo log header
					on the segment header page, 0 if
					none */
#define	TRX_UNDO_FSEG_HEADER	4	/* Header for the file segment which
					the undo log segment occupies */
#define	TRX_UNDO_PAGE_LIST	(4 + FSEG_HEADER_SIZE)
					/* Base node for the list of pages in
					the undo log segment; defined only on
					the undo log segment's first page */
/*-------------------------------------------------------------*/
/* Size of the undo log segment header */
#define TRX_UNDO_SEG_HDR_SIZE	(4 + FSEG_HEADER_SIZE + FLST_BASE_NODE_SIZE)


/* The undo log header. There can be several undo log headers on the first
page of an update undo log segment. */
/*-------------------------------------------------------------*/
#define	TRX_UNDO_TRX_ID		0	/* Transaction id */
#define	TRX_UNDO_TRX_NO		8	/* Transaction number of the
					transaction; defined only if the log
					is in a history list */
#define TRX_UNDO_DEL_MARKS	16	/* Defined only in an update undo
					log: TRUE if the transaction may have
					done delete markings of records, and
					thus purge is necessary */
#define	TRX_UNDO_LOG_START	18	/* Offset of the first undo log record
					of this log on the header page; purge
					may remove undo log record from the
					log start, and therefore this is not
					necessarily the same as this log
					header end offset */
#define	TRX_UNDO_XID_EXISTS	20	/* TRUE if undo log header includes
					X/Open XA transaction identification
					XID */
#define	TRX_UNDO_DICT_TRANS	21	/* TRUE if the transaction is a table
					create, index create, or drop
					transaction: in recovery
					the transaction cannot be rolled back
					in the usual way: a 'rollback' rather
					means dropping the created or dropped
					table, if it still exists */
#define TRX_UNDO_TABLE_ID	22	/* Id of the table if the preceding
					field is TRUE */
#define	TRX_UNDO_NEXT_LOG	30	/* Offset of the next undo log header
					on this page, 0 if none */
#define	TRX_UNDO_PREV_LOG	32	/* Offset of the previous undo log
					header on this page, 0 if none */
#define TRX_UNDO_HISTORY_NODE	34	/* If the log is put to the history
					list, the file list node is here */
/*-------------------------------------------------------------*/
#define TRX_UNDO_LOG_OLD_HDR_SIZE (34 + FLST_NODE_SIZE)

/* Note: the writing of the undo log old header is coded by a log record
MLOG_UNDO_HDR_CREATE or MLOG_UNDO_HDR_REUSE. The appending of an XID to the
header is logged separately. In this sense, the XID is not really a member
of the undo log header. TODO: do not append the XID to the log header if XA
is not needed by the user. The XID wastes about 150 bytes of space in every
undo log. In the history list we may have millions of undo logs, which means
quite a large overhead. */

/* X/Open XA Transaction Identification (XID) */

#define	TRX_UNDO_XA_FORMAT	(TRX_UNDO_LOG_OLD_HDR_SIZE)
#define	TRX_UNDO_XA_TRID_LEN	(TRX_UNDO_XA_FORMAT + 4)
#define	TRX_UNDO_XA_BQUAL_LEN	(TRX_UNDO_XA_TRID_LEN + 4)
#define	TRX_UNDO_XA_XID		(TRX_UNDO_XA_BQUAL_LEN + 4)
/*--------------------------------------------------------------*/
#define TRX_UNDO_LOG_XA_HDR_SIZE (TRX_UNDO_XA_XID + XIDDATASIZE)
				/* Total size of the header with the XA XID */

#ifndef UNIV_NONINL
#include "trx0undo.ic"
#endif

#endif