Commit f7674d43 authored by marko's avatar marko

branches/zip: Distinguish temporary tables in MLOG_FILE_CREATE.

This addresses Mantis Issue #23 in InnoDB Hot Backup and some
of MySQL Bug #41609.

In MLOG_FILE_CREATE, we need to distinguish temporary tables, so that
InnoDB Hot Backup can work correctly.  It turns out that we can do this
easily, by using a bit of the previously unused parameter for page number.
(The page number parameter of MLOG_FILE_CREATE has been written as 0 
ever since MySQL 4.1, which introduced MLOG_FILE_CREATE.)

MLOG_FILE_FLAG_TEMP: A flag for indicating a temporary table in
the page number parameter of MLOG_FILE_ operations.

fil_op_write_log(): Add the parameter log_flags.

fil_op_log_parse_or_replay(): Add the parameter log_flags.
Do not replay MLOG_FILE_CREATE when MLOG_FILE_FLAG_TEMP is set in log_flags.
This only affects ibbackup --apply-log.  InnoDB itself never replays file
operations.

rb://117 approved by Heikki Tuuri
parent 80e0aca3
......@@ -1870,6 +1870,8 @@ fil_op_write_log(
MLOG_FILE_DELETE, or
MLOG_FILE_RENAME */
ulint space_id, /* in: space id */
ulint log_flags, /* in: redo log flags (stored
in the page number field) */
ulint flags, /* in: compressed page size
and file format
if type==MLOG_FILE_CREATE2, or 0 */
......@@ -1893,8 +1895,8 @@ fil_op_write_log(
return;
}
log_ptr = mlog_write_initial_log_record_for_file_op(type, space_id, 0,
log_ptr, mtr);
log_ptr = mlog_write_initial_log_record_for_file_op(
type, space_id, log_flags, log_ptr, mtr);
if (type == MLOG_FILE_CREATE2) {
mach_write_to_4(log_ptr, flags);
log_ptr += 4;
......@@ -1947,9 +1949,11 @@ fil_op_log_parse_or_replay(
not fir completely between ptr and end_ptr */
byte* end_ptr, /* in: buffer end */
ulint type, /* in: the type of this log record */
ulint space_id) /* in: the space id of the tablespace in
ulint space_id, /* in: the space id of the tablespace in
question, or 0 if the log record should
only be parsed but not replayed */
ulint log_flags) /* in: redo log flags
(stored in the page number parameter) */
{
ulint name_len;
ulint new_name_len;
......@@ -2069,6 +2073,8 @@ fil_op_log_parse_or_replay(
} else if (fil_get_space_id_for_table(name)
!= ULINT_UNDEFINED) {
/* Do nothing */
} else if (log_flags & MLOG_FILE_FLAG_TEMP) {
/* Temporary table, do nothing */
} else {
/* Create the database directory for name, if it does
not exist yet */
......@@ -2232,7 +2238,7 @@ try_again:
to write any log record */
mtr_start(&mtr);
fil_op_write_log(MLOG_FILE_DELETE, id, 0, path, NULL, &mtr);
fil_op_write_log(MLOG_FILE_DELETE, id, 0, 0, path, NULL, &mtr);
mtr_commit(&mtr);
#endif
mem_free(path);
......@@ -2503,7 +2509,7 @@ retry:
mtr_start(&mtr);
fil_op_write_log(MLOG_FILE_RENAME, id, 0, old_name, new_name,
fil_op_write_log(MLOG_FILE_RENAME, id, 0, 0, old_name, new_name,
&mtr);
mtr_commit(&mtr);
}
......@@ -2707,7 +2713,9 @@ error_exit2:
fil_op_write_log(flags
? MLOG_FILE_CREATE2
: MLOG_FILE_CREATE,
*space_id, flags,
*space_id,
is_temp ? MLOG_FILE_FLAG_TEMP : 0,
flags,
tablename, NULL, &mtr);
mtr_commit(&mtr);
......
......@@ -365,9 +365,11 @@ fil_op_log_parse_or_replay(
not fir completely between ptr and end_ptr */
byte* end_ptr, /* in: buffer end */
ulint type, /* in: the type of this log record */
ulint space_id); /* in: the space id of the tablespace in
ulint space_id, /* in: the space id of the tablespace in
question, or 0 if the log record should
only be parsed but not replayed */
ulint log_flags); /* in: redo log flags
(stored in the page number parameter) */
/***********************************************************************
Deletes a single-table tablespace. The tablespace must be cached in the
memory cache. */
......
......@@ -160,6 +160,12 @@ flag value must give the length also! */
#define MLOG_BIGGEST_TYPE ((byte)51) /* biggest value (used in
asserts) */
/* Flags for MLOG_FILE operations (stored in the page number
parameter, called log_flags in the functions). The page number
parameter was initially written as 0. */
#define MLOG_FILE_FLAG_TEMP 1 /* identifies TEMPORARY TABLE in
MLOG_FILE_CREATE, MLOG_FILE_CREATE2 */
/*******************************************************************
Starts a mini-transaction and creates a mini-transaction handle
and buffer in the memory buffer given by the caller. */
......
......@@ -1089,7 +1089,7 @@ recv_parse_or_apply_log_rec_body(
case MLOG_FILE_RENAME:
case MLOG_FILE_DELETE:
case MLOG_FILE_CREATE2:
ptr = fil_op_log_parse_or_replay(ptr, end_ptr, type, 0);
ptr = fil_op_log_parse_or_replay(ptr, end_ptr, type, 0, 0);
break;
case MLOG_ZIP_WRITE_NODE_PTR:
ut_ad(!page || page_type == FIL_PAGE_INDEX);
......@@ -2139,7 +2139,8 @@ loop:
point to the datadir we should use there */
if (NULL == fil_op_log_parse_or_replay(
body, end_ptr, type, space)) {
body, end_ptr, type,
space, page_no)) {
fprintf(stderr,
"InnoDB: Error: file op"
" log record of type %lu"
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment