Commit 8e49d20d authored by unknown's avatar unknown

Postreview changes.

Fixed befaviour when loghandler flags changed from one
run to another one.
Description of maria transaction log and control file
added to the file commandÍs magic number file.


mysys/mf_pagecache.c:
  postreview changes
storage/maria/ma_control_file.c:
  Postreview changes.
storage/maria/ma_control_file.h:
  Postreview changes.
storage/maria/ma_loghandler.c:
  Postreview changes.
  Fixed befaviour when loghandler flags changed from
  one run to another one.
storage/maria/ma_loghandler.h:
  Postreview changes.
  Functions comment left only near the function body.
storage/maria/ma_loghandler_lsn.h:
  Postreview changes.
storage/maria/unittest/ma_test_loghandler-t.c:
  Postreview changes.
storage/maria/unittest/ma_test_loghandler_multigroup-t.c:
  Postreview changes.
storage/maria/unittest/ma_test_loghandler_multithread-t.c:
  Postreview changes.
storage/maria/unittest/ma_test_loghandler_pagecache-t.c:
  Postreview changes.
support-files/magic:
  Description of maria transaction log and control file
  added to the file commandÕs magic number file.
parent 1f59a95c
......@@ -570,7 +570,7 @@ static uint pagecache_fwrite(PAGECACHE *pagecache,
DBUG_PRINT("info", ("Log handler call"));
/* TODO: integrate with page format */
#define PAGE_LSN_OFFSET 0
lsn= lsn7korr(buffer + PAGE_LSN_OFFSET);
lsn= lsn_korr(buffer + PAGE_LSN_OFFSET);
/*
check CONTROL_FILE_IMPOSSIBLE_FILENO &
CONTROL_FILE_IMPOSSIBLE_LOG_OFFSET
......
......@@ -21,7 +21,6 @@
*/
#include "maria_def.h"
#include "ma_control_file.h"
/* Here is the implementation of this module */
......@@ -31,13 +30,13 @@
*/
/* total size should be < sector size for atomic write operation */
#define CONTROL_FILE_MAGIC_STRING "MACF"
#define CONTROL_FILE_MAGIC_STRING "\xfe\xfe\xc\1MACF"
#define CONTROL_FILE_MAGIC_STRING_OFFSET 0
#define CONTROL_FILE_MAGIC_STRING_SIZE (sizeof(CONTROL_FILE_MAGIC_STRING)-1)
#define CONTROL_FILE_CHECKSUM_OFFSET (CONTROL_FILE_MAGIC_STRING_OFFSET + CONTROL_FILE_MAGIC_STRING_SIZE)
#define CONTROL_FILE_CHECKSUM_SIZE 1
#define CONTROL_FILE_LSN_OFFSET (CONTROL_FILE_CHECKSUM_OFFSET + CONTROL_FILE_CHECKSUM_SIZE)
#define CONTROL_FILE_LSN_SIZE (3+4)
#define CONTROL_FILE_LSN_SIZE LSN_STORE_SIZE
#define CONTROL_FILE_FILENO_OFFSET (CONTROL_FILE_LSN_OFFSET + CONTROL_FILE_LSN_SIZE)
#define CONTROL_FILE_FILENO_SIZE 4
#define CONTROL_FILE_SIZE (CONTROL_FILE_FILENO_OFFSET + CONTROL_FILE_FILENO_SIZE)
......@@ -200,7 +199,7 @@ CONTROL_FILE_ERROR ma_control_file_create_or_open()
error= CONTROL_FILE_BAD_CHECKSUM;
goto err;
}
last_checkpoint_lsn= lsn7korr(buffer + CONTROL_FILE_LSN_OFFSET);
last_checkpoint_lsn= lsn_korr(buffer + CONTROL_FILE_LSN_OFFSET);
last_logno= uint4korr(buffer + CONTROL_FILE_FILENO_OFFSET);
DBUG_RETURN(0);
......@@ -261,9 +260,9 @@ int ma_control_file_write_and_force(const LSN checkpoint_lsn, uint32 logno,
DBUG_ASSERT(0);
if (update_checkpoint_lsn)
lsn7store(buffer + CONTROL_FILE_LSN_OFFSET, checkpoint_lsn);
lsn_store(buffer + CONTROL_FILE_LSN_OFFSET, checkpoint_lsn);
else /* store old value == change nothing */
lsn7store(buffer + CONTROL_FILE_LSN_OFFSET, last_checkpoint_lsn);
lsn_store(buffer + CONTROL_FILE_LSN_OFFSET, last_checkpoint_lsn);
if (update_logno)
int4store(buffer + CONTROL_FILE_FILENO_OFFSET, logno);
......
......@@ -19,9 +19,6 @@
First version written by Guilhem Bichot on 2006-04-27.
*/
#ifndef _ma_control_file_h
#define _ma_control_file_h
#define CONTROL_FILE_BASE_NAME "maria_control"
/*
indicate absence of the log file number; first log is always number 1, 0 is
......@@ -47,11 +44,6 @@ extern LSN last_checkpoint_lsn;
*/
extern uint32 last_logno;
/*
Looks for the control file. If absent, it's a fresh start, create file.
If present, read it to find out last checkpoint's LSN and last log.
Called at engine's start.
*/
typedef enum enum_control_file_error {
CONTROL_FILE_OK= 0,
CONTROL_FILE_TOO_SMALL,
......@@ -60,21 +52,26 @@ typedef enum enum_control_file_error {
CONTROL_FILE_BAD_CHECKSUM,
CONTROL_FILE_UNKNOWN_ERROR /* any other error */
} CONTROL_FILE_ERROR;
CONTROL_FILE_ERROR ma_control_file_create_or_open();
#define CONTROL_FILE_UPDATE_ALL 0
#define CONTROL_FILE_UPDATE_ONLY_LSN 1
#define CONTROL_FILE_UPDATE_ONLY_LOGNO 2
/*
Looks for the control file. If absent, it's a fresh start, create file.
If present, read it to find out last checkpoint's LSN and last log.
Called at engine's start.
*/
CONTROL_FILE_ERROR ma_control_file_create_or_open();
/*
Write information durably to the control file.
Called when we have created a new log (after syncing this log's creation)
and when we have written a checkpoint (after syncing this log record).
*/
#define CONTROL_FILE_UPDATE_ALL 0
#define CONTROL_FILE_UPDATE_ONLY_LSN 1
#define CONTROL_FILE_UPDATE_ONLY_LOGNO 2
int ma_control_file_write_and_force(const LSN checkpoint_lsn, uint32 logno,
uint objs_to_write);
/* Free resources taken by control file subsystem */
int ma_control_file_end();
#endif
This source diff could not be displayed because it is too large. You can view the blob instead.
#ifndef _ma_loghandler_h
#define _ma_loghandler_h
/* Transaction log flags */
#define TRANSLOG_PAGE_CRC 1
#define TRANSLOG_SECTOR_PROTECTION (1<<1)
#define TRANSLOG_RECORD_CRC (1<<2)
#define TRANSLOG_FLAGS_NUM ((TRANSLOG_PAGE_CRC | TRANSLOG_SECTOR_PROTECTION | \
TRANSLOG_RECORD_CRC) + 1)
/* page size in transaction log */
/*
Page size in transaction log
It should be Power of 2 and multiple of DISK_DRIVE_SECTOR_SIZE
(DISK_DRIVE_SECTOR_SIZE * 2^N)
*/
#define TRANSLOG_PAGE_SIZE (8*1024)
#include "ma_loghandler_lsn.h"
......@@ -15,6 +18,14 @@
/* short transaction ID type */
typedef uint16 SHORT_TRANSACTION_ID;
/* Length of CRC at end of pages */
#define CRC_LENGTH 4
/*
Length of disk drive sector size (we assume that writing it
to disk is atomic operation)
*/
#define DISK_DRIVE_SECTOR_SIZE 512
/* types of records in the transaction log */
enum translog_record_type
{
......@@ -51,8 +62,9 @@ enum translog_record_type
LOGREC_LONG_TRANSACTION_ID= 30,
LOGREC_RESERVED_FUTURE_EXTENSION= 63
};
#define LOGREC_NUMBER_OF_TYPES 64
#define LOGREC_NUMBER_OF_TYPES 64 /* Maximum, can't be extended */
/* Size of log file; One log file is restricted to 4G */
typedef uint32 translog_size_t;
#define TRANSLOG_RECORD_HEADER_MAX_SIZE 1024
......@@ -68,8 +80,8 @@ typedef struct st_translog_header_buffer
{
/* LSN of the read record */
LSN lsn;
/* type of the read record */
enum translog_record_type type;
/* array of groups descriptors, can be used only if groups_no > 0 */
TRANSLOG_GROUP *groups;
/* short transaction ID or 0 if it has no sense for the record */
SHORT_TRANSACTION_ID short_trid;
/*
......@@ -77,56 +89,56 @@ typedef struct st_translog_header_buffer
hidden part of record (type, short TrID, length)
*/
translog_size_t record_length;
/*
Real compressed LSN(s) size economy (<number of LSN(s)>*7 - <real_size>)
*/
uint16 compressed_LSN_economy;
/*
Buffer for write decoded header of the record (depend on the record
type)
*/
uchar header[TRANSLOG_RECORD_HEADER_MAX_SIZE];
/* non read body data offset on the page */
uint16 non_header_data_start_offset;
/* non read body data length in this first chunk */
uint16 non_header_data_len;
byte header[TRANSLOG_RECORD_HEADER_MAX_SIZE];
/* number of groups listed in */
uint groups_no;
/* array of groups descriptors, can be used only if groups_no > 0 */
TRANSLOG_GROUP *groups;
/* in multi-group number of chunk0 pages (valid only if groups_no > 0) */
uint chunk0_pages;
/* type of the read record */
enum translog_record_type type;
/* chunk 0 data address (valid only if groups_no > 0) */
TRANSLOG_ADDRESS chunk0_data_addr;
/*
Real compressed LSN(s) size economy (<number of LSN(s)>*7 - <real_size>)
*/
uint16 compressed_LSN_economy;
/* short transaction ID or 0 if it has no sense for the record */
uint16 non_header_data_start_offset;
/* non read body data length in this first chunk */
uint16 non_header_data_len;
/* chunk 0 data size (valid only if groups_no > 0) */
uint16 chunk0_data_len;
} TRANSLOG_HEADER_BUFFER;
struct st_translog_scanner_data
typedef struct st_translog_scanner_data
{
uchar buffer[TRANSLOG_PAGE_SIZE]; /* buffer for page content */
TRANSLOG_ADDRESS page_addr; /* current page address */
TRANSLOG_ADDRESS horizon; /* end of the log which we saw
last time */
TRANSLOG_ADDRESS last_file_page; /* Last page on in this file */
uchar *page; /* page content pointer */
translog_size_t page_offset; /* offset of the chunk in the
page */
my_bool fixed_horizon; /* set horizon only once at
init */
};
byte buffer[TRANSLOG_PAGE_SIZE]; /* buffer for page content */
TRANSLOG_ADDRESS page_addr; /* current page address */
/* end of the log which we saw last time */
TRANSLOG_ADDRESS horizon;
TRANSLOG_ADDRESS last_file_page; /* Last page on in this file */
byte *page; /* page content pointer */
/* offset of the chunk in the page */
translog_size_t page_offset;
/* set horizon only once at init */
my_bool fixed_horizon;
} TRANSLOG_SCANNER_DATA;
struct st_translog_reader_data
{
TRANSLOG_HEADER_BUFFER header; /* Header */
struct st_translog_scanner_data scanner; /* chunks scanner */
TRANSLOG_SCANNER_DATA scanner; /* chunks scanner */
translog_size_t body_offset; /* current chunk body offset */
translog_size_t current_offset; /* data offset from the record
beginning */
uint16 read_header; /* number of bytes read in
header */
/* data offset from the record beginning */
translog_size_t current_offset;
/* number of bytes read in header */
uint16 read_header;
uint16 chunk_size; /* current chunk size */
uint current_group; /* current group */
uint current_chunk; /* current chunk in the group */
......@@ -134,181 +146,37 @@ struct st_translog_reader_data
};
/*
Initialize transaction log
SYNOPSIS
translog_init()
directory Directory where log files are put
log_file_max_size max size of one log size (for new logs creation)
server_version version of MySQL servger (MYSQL_VERSION_ID)
server_id server ID (replication & Co)
pagecache Page cache for the log reads
flags flags (TRANSLOG_PAGE_CRC, TRANSLOG_SECTOR_PROTECTION
TRANSLOG_RECORD_CRC)
RETURN
0 - OK
1 - Error
*/
my_bool translog_init(const char *directory, uint32 log_file_max_size,
uint32 server_version,
uint32 server_id, PAGECACHE *pagecache, uint flags);
/*
Write the log record
SYNOPSIS
translog_write_record()
lsn LSN of the record will be writen here
type the log record type
short_trid Sort transaction ID or 0 if it has no sense
tcb Transaction control block pointer for hooks by
record log type
partN_length length of Ns part of the log
partN_buffer pointer on Ns part buffer
0 sign of the end of parts
RETURN
0 - OK
1 - Error
*/
uint32 server_version, uint32 server_id,
PAGECACHE *pagecache, uint flags);
my_bool translog_write_record(LSN *lsn,
enum translog_record_type type,
SHORT_TRANSACTION_ID short_trid,
void *tcb,
translog_size_t part1_length,
uchar *part1_buff, ...);
/*
Free log handler resources
SYNOPSIS
translog_destroy()
*/
byte *part1_buff, ...);
void translog_destroy();
/*
Read record header and some fixed part of a record (the part depend on
record type).
SYNOPSIS
translog_read_record_header()
lsn log record serial number (address of the record)
buff log record header buffer
NOTE
- lsn can point to TRANSLOG_HEADER_BUFFER::lsn and it will be processed
correctly.
- Some type of record can be read completely by this call
- "Decoded" header stored in TRANSLOG_HEADER_BUFFER::header (relative
LSN can be translated to absolute one), some fields can be added
(like actual header length in the record if the header has variable
length)
RETURN
0 - error
number of bytes in TRANSLOG_HEADER_BUFFER::header where stored decoded
part of the header
*/
translog_size_t translog_read_record_header(LSN lsn,
TRANSLOG_HEADER_BUFFER *buff);
/*
Free resources used by TRANSLOG_HEADER_BUFFER
SYNOPSIS
translog_free_record_header();
*/
void translog_free_record_header(TRANSLOG_HEADER_BUFFER *buff);
/*
Read a part of the record.
SYNOPSIS
translog_read_record_header()
lsn log record serial number (address of the record)
offset from the beginning of the record beginning (read
by translog_read_record_header).
length length of record part which have to be read.
buffer buffer where to read the record part (have to be at
least 'length' bytes length)
RETURN
0 - error (or read out of the record)
length of data actually read
*/
translog_size_t translog_read_record(LSN lsn,
translog_size_t offset,
translog_size_t length,
uchar *buffer,
byte *buffer,
struct st_translog_reader_data *data);
/*
Flush the log up to given LSN (included)
SYNOPSIS
translog_flush()
lsn log record serial number up to which (inclusive)
the log have to be flushed
RETURN
0 - OK
1 - Error
*/
my_bool translog_flush(LSN lsn);
my_bool translog_init_scanner(LSN lsn,
my_bool fixed_horizon,
struct st_translog_scanner_data *scanner);
/*
Read record header and some fixed part of the next record (the part
depend on record type).
SYNOPSIS
translog_read_next_record_header()
lsn log record serial number (address of the record)
previous to the record which will be read
If LSN present scanner will be initialized from it,
do not use LSN after initialization for fast scanning.
buff log record header buffer
fixed_horizon true if it is OK do not read records which was written
after scaning begining
scanner data for scaning if lsn is NULL scanner data
will be used for continue scaning.
scanner can be NULL.
NOTE
- lsn can point to TRANSLOG_HEADER_BUFFER::lsn and it will be processed
correctly (lsn in buffer will be replaced by next record, but initial
lsn will be read correctly).
- it is like translog_read_record_header, but read next record, so see
its NOTES.
- in case of end of the log buff->lsn will be set to
(CONTROL_FILE_IMPOSSIBLE_LOGNO, 0)
RETURN
0 - error
TRANSLOG_RECORD_HEADER_MAX_SIZE + 1 - End of the log
number of bytes in TRANSLOG_HEADER_BUFFER::header where stored decoded
part of the header
*/
translog_size_t translog_read_next_record_header(LSN lsn,
TRANSLOG_HEADER_BUFFER *buff,
my_bool fixed_horizon,
struct
st_translog_scanner_data
*scanner);
translog_size_t translog_read_next_record_header(TRANSLOG_SCANNER_DATA
*scanner,
TRANSLOG_HEADER_BUFFER *buff);
#endif
......@@ -30,15 +30,18 @@ typedef TRANSLOG_ADDRESS LSN;
/* checks LSN */
#define LSN_VALID(L) DBUG_ASSERT((L) >= 0 && (L) < (uint64)0xFFFFFFFFFFFFFFLL)
/* size of stored LSN on a disk */
#define LSN_STORE_SIZE 7
/* Puts LSN into buffer (dst) */
#define lsn7store(dst, lsn) \
#define lsn_store(dst, lsn) \
do { \
int3store((dst), LSN_FILE_NO(lsn)); \
int4store((dst) + 3, LSN_OFFSET(lsn)); \
} while (0)
/* Unpacks LSN from the buffer (P) */
#define lsn7korr(P) MAKE_LSN(uint3korr(P), uint4korr((P) + 3))
#define lsn_korr(P) MAKE_LSN(uint3korr(P), uint4korr((P) + 3))
/* what we need to add to LSN to increase it on one file */
#define LSN_ONE_FILE ((int64)0x100000000LL)
......
......@@ -47,10 +47,10 @@ static const char *default_dbug_option;
1 - Error
*/
static my_bool check_content(uchar *ptr, ulong length)
static my_bool check_content(byte *ptr, ulong length)
{
ulong i;
uchar buff[2];
byte buff[2];
for (i= 0; i < length; i++)
{
if (i % 2 == 0)
......@@ -81,7 +81,7 @@ static my_bool check_content(uchar *ptr, ulong length)
*/
static my_bool read_and_check_content(TRANSLOG_HEADER_BUFFER *rec,
uchar *buffer, uint skip)
byte *buffer, uint skip)
{
DBUG_ASSERT(rec->record_length < LONG_BUFFER_SIZE * 2 + 7 * 2 + 2);
if (translog_read_record(rec->lsn, 0, rec->record_length, buffer, NULL) !=
......@@ -95,16 +95,16 @@ int main(int argc, char *argv[])
uint32 i;
uint32 rec_len;
uint pagen;
uchar long_tr_id[6];
uchar lsn_buff[23]=
byte long_tr_id[6];
byte lsn_buff[23]=
{
0x55, 0xAA, 0x55, 0xAA, 0x55, 0xAA, 0x55, 0xAA,
0x55, 0xAA, 0x55, 0xAA, 0x55, 0xAA, 0x55, 0xAA,
0x55, 0xAA, 0x55, 0xAA, 0x55, 0xAA, 0x55
};
uchar long_buffer[LONG_BUFFER_SIZE * 2 + 7 * 2 + 2];
byte long_buffer[LONG_BUFFER_SIZE * 2 + LSN_STORE_SIZE * 2 + 2];
PAGECACHE pagecache;
LSN lsn, lsn_base, first_lsn, lsn_ptr;
LSN lsn, lsn_base, first_lsn;
TRANSLOG_HEADER_BUFFER rec;
struct st_translog_scanner_data scanner;
int rc;
......@@ -114,7 +114,7 @@ int main(int argc, char *argv[])
bzero(&pagecache, sizeof(pagecache));
maria_data_root= ".";
for (i= 0; i < (LONG_BUFFER_SIZE + 7 * 2 + 2); i+= 2)
for (i= 0; i < (LONG_BUFFER_SIZE + LSN_STORE_SIZE * 2 + 2); i+= 2)
{
int2store(long_buffer + i, (i >> 1));
/* long_buffer[i]= (i & 0xFF); */
......@@ -173,7 +173,7 @@ int main(int argc, char *argv[])
printf("write %d\n", i);
if (i % 2)
{
lsn7store(lsn_buff, lsn_base);
lsn_store(lsn_buff, lsn_base);
if (translog_write_record(&lsn,
LOGREC_CLR_END,
(i % 0xFFFF), NULL, 7, lsn_buff, 0))
......@@ -183,7 +183,7 @@ int main(int argc, char *argv[])
translog_destroy();
exit(1);
}
lsn7store(lsn_buff, lsn_base);
lsn_store(lsn_buff, lsn_base);
if ((rec_len= random() / (RAND_MAX / (LONG_BUFFER_SIZE + 1))) < 12)
rec_len= 12;
if (translog_write_record(&lsn,
......@@ -199,8 +199,8 @@ int main(int argc, char *argv[])
}
else
{
lsn7store(lsn_buff, lsn_base);
lsn7store(lsn_buff + 7, first_lsn);
lsn_store(lsn_buff, lsn_base);
lsn_store(lsn_buff + LSN_STORE_SIZE, first_lsn);
if (translog_write_record(&lsn,
LOGREC_UNDO_ROW_DELETE,
(i % 0xFFFF), NULL, 23, lsn_buff, 0))
......@@ -210,8 +210,8 @@ int main(int argc, char *argv[])
translog_destroy();
exit(1);
}
lsn7store(lsn_buff, lsn_base);
lsn7store(lsn_buff + 7, first_lsn);
lsn_store(lsn_buff, lsn_base);
lsn_store(lsn_buff + LSN_STORE_SIZE, first_lsn);
if ((rec_len= random() / (RAND_MAX / (LONG_BUFFER_SIZE + 1))) < 19)
rec_len= 19;
if (translog_write_record(&lsn,
......@@ -291,7 +291,7 @@ int main(int argc, char *argv[])
}
if (rec.type !=LOGREC_LONG_TRANSACTION_ID || rec.short_trid != 0 ||
rec.record_length != 6 || uint4korr(rec.header) != 0 ||
(uint)rec.header[4] != 0 || rec.header[5] != 0xFF ||
((uchar)rec.header[4]) != 0 || ((uchar)rec.header[5]) != 0xFF ||
first_lsn != rec.lsn)
{
fprintf(stderr, "Incorrect LOGREC_LONG_TRANSACTION_ID data read(0)\n"
......@@ -304,12 +304,16 @@ int main(int argc, char *argv[])
goto err;
}
lsn= first_lsn;
lsn_ptr= first_lsn;
if (translog_init_scanner(first_lsn, 1, &scanner))
{
fprintf(stderr, "scanner init failed\n");
goto err;
}
for (i= 1;; i++)
{
if (i % 1000 == 0)
printf("read %d\n", i);
len= translog_read_next_record_header(lsn_ptr, &rec, 1, &scanner);
len= translog_read_next_record_header(&scanner, &rec);
if (len == 0)
{
fprintf(stderr, "1-%d translog_read_next_record_header failed (%d)\n",
......@@ -326,21 +330,21 @@ int main(int argc, char *argv[])
}
break;
}
/* use scanner after its initialization */
lsn_ptr= 0;
if (i % 2)
{
LSN ref;
ref= lsn7korr(rec.header);
ref= lsn_korr(rec.header);
if (rec.type !=LOGREC_CLR_END || rec.short_trid != (i % 0xFFFF) ||
rec.record_length != 7 || ref != lsn)
{
fprintf(stderr, "Incorrect LOGREC_CLR_END data read(%d) "
"type %u, strid %u, len %u, ref(%lu,0x%lx), "
"type: %u strid: %u len: %u"
"ref: (%lu,0x%lx) (%lu,0x%lx) "
"lsn(%lu,0x%lx)\n",
i, (uint) rec.type, (uint) rec.short_trid,
(uint) rec.record_length,
(ulong) LSN_FILE_NO(ref), (ulong) LSN_OFFSET(ref),
(ulong) LSN_FILE_NO(lsn), (ulong) LSN_OFFSET(lsn),
(ulong) LSN_FILE_NO(rec.lsn), (ulong) LSN_OFFSET(rec.lsn));
goto err;
}
......@@ -348,18 +352,22 @@ int main(int argc, char *argv[])
else
{
LSN ref1, ref2;
ref1= lsn7korr(rec.header);
ref2= lsn7korr(rec.header + 7);
if (rec.type !=LOGREC_UNDO_ROW_DELETE ||
ref1= lsn_korr(rec.header);
ref2= lsn_korr(rec.header + LSN_STORE_SIZE);
if (rec.type != LOGREC_UNDO_ROW_DELETE ||
rec.short_trid != (i % 0xFFFF) ||
rec.record_length != 23 ||
ref1 != lsn ||
ref2 != first_lsn ||
rec.header[22] != 0x55 || rec.header[21] != 0xAA ||
rec.header[20] != 0x55 || rec.header[19] != 0xAA ||
rec.header[18] != 0x55 || rec.header[17] != 0xAA ||
rec.header[16] != 0x55 || rec.header[15] != 0xAA ||
rec.header[14] != 0x55)
((uchar)rec.header[22]) != 0x55 ||
((uchar)rec.header[21]) != 0xAA ||
((uchar)rec.header[20]) != 0x55 ||
((uchar)rec.header[19]) != 0xAA ||
((uchar)rec.header[18]) != 0x55 ||
((uchar)rec.header[17]) != 0xAA ||
((uchar)rec.header[16]) != 0x55 ||
((uchar)rec.header[15]) != 0xAA ||
((uchar)rec.header[14]) != 0x55)
{
fprintf(stderr, "Incorrect LOGREC_UNDO_ROW_DELETE data read(%d)"
"type %u, strid %u, len %u, ref1(%lu,0x%lx), "
......@@ -378,7 +386,7 @@ int main(int argc, char *argv[])
goto err;
}
}
len= translog_read_next_record_header(lsn_ptr, &rec, 1, &scanner);
len= translog_read_next_record_header(&scanner, &rec);
if (len == 0)
{
fprintf(stderr, "1-%d translog_read_next_record_header (var) "
......@@ -394,14 +402,14 @@ int main(int argc, char *argv[])
if (i % 2)
{
LSN ref;
ref= lsn7korr(rec.header);
ref= lsn_korr(rec.header);
if ((rec_len= random() / (RAND_MAX / (LONG_BUFFER_SIZE + 1))) < 12)
rec_len= 12;
if (rec.type !=LOGREC_UNDO_KEY_INSERT ||
rec.short_trid != (i % 0xFFFF) ||
rec.record_length != rec_len + 7 ||
rec.record_length != rec_len + LSN_STORE_SIZE ||
len != 12 || ref != lsn ||
check_content(rec.header + 7, len - 7))
check_content(rec.header + LSN_STORE_SIZE, len - LSN_STORE_SIZE))
{
fprintf(stderr, "Incorrect LOGREC_UNDO_KEY_INSERT data read(%d)"
"type %u (%d), strid %u (%d), len %lu, %lu + 7 (%d), "
......@@ -412,16 +420,17 @@ int main(int argc, char *argv[])
(uint) rec.short_trid,
rec.short_trid != (i % 0xFFFF),
(ulong) rec.record_length, (ulong) rec_len,
rec.record_length != rec_len + 7,
rec.record_length != rec_len + LSN_STORE_SIZE,
(uint) len,
len != 12,
(ulong) LSN_FILE_NO(ref), (ulong) LSN_OFFSET(ref),
(ulong) LSN_FILE_NO(rec.lsn), (ulong) LSN_OFFSET(rec.lsn),
(len != 12 || ref != lsn),
check_content(rec.header + 7, len - 7));
check_content(rec.header + LSN_STORE_SIZE,
len - LSN_STORE_SIZE));
goto err;
}
if (read_and_check_content(&rec, long_buffer, 7))
if (read_and_check_content(&rec, long_buffer, LSN_STORE_SIZE))
{
fprintf(stderr,
"Incorrect LOGREC_UNDO_KEY_INSERT in whole rec read "
......@@ -433,20 +442,21 @@ int main(int argc, char *argv[])
else
{
LSN ref1, ref2;
ref1= lsn7korr(rec.header);
ref2= lsn7korr(rec.header + 7);
ref1= lsn_korr(rec.header);
ref2= lsn_korr(rec.header + LSN_STORE_SIZE);
if ((rec_len= random() / (RAND_MAX / (LONG_BUFFER_SIZE + 1))) < 19)
rec_len= 19;
if (rec.type !=LOGREC_UNDO_KEY_DELETE ||
rec.short_trid != (i % 0xFFFF) ||
rec.record_length != rec_len + 14 ||
rec.record_length != rec_len + LSN_STORE_SIZE * 2 ||
len != 19 ||
ref1 != lsn ||
ref2 != first_lsn ||
check_content(rec.header + 14, len - 14))
check_content(rec.header + LSN_STORE_SIZE * 2,
len - LSN_STORE_SIZE * 2))
{
fprintf(stderr, "Incorrect LOGREC_UNDO_KEY_DELETE data read(%d)"
"type %u, strid %u, len %lu != %lu + 7, hdr len: %u, "
"type %u, strid %u, len %lu != %lu + 14, hdr len: %u, "
"ref1(%lu,0x%lx), ref2(%lu,0x%lx), "
"lsn(%lu,0x%lx)\n",
i, (uint) rec.type, (uint) rec.short_trid,
......@@ -457,7 +467,7 @@ int main(int argc, char *argv[])
(ulong) LSN_FILE_NO(rec.lsn), (ulong) LSN_OFFSET(rec.lsn));
goto err;
}
if (read_and_check_content(&rec, long_buffer, 14))
if (read_and_check_content(&rec, long_buffer, LSN_STORE_SIZE * 2))
{
fprintf(stderr,
"Incorrect LOGREC_UNDO_KEY_DELETE in whole rec read "
......@@ -467,7 +477,7 @@ int main(int argc, char *argv[])
}
}
len= translog_read_next_record_header(lsn_ptr, &rec, 1, &scanner);
len= translog_read_next_record_header(&scanner, &rec);
if (len == 0)
{
fprintf(stderr, "1-%d translog_read_next_record_header failed (%d)\n",
......@@ -483,7 +493,7 @@ int main(int argc, char *argv[])
if (rec.type !=LOGREC_LONG_TRANSACTION_ID ||
rec.short_trid != (i % 0xFFFF) ||
rec.record_length != 6 || uint4korr(rec.header) != i ||
rec.header[4] != 0 || rec.header[5] != 0xFF)
((uchar)rec.header[4]) != 0 || ((uchar)rec.header[5]) != 0xFF)
{
fprintf(stderr, "Incorrect LOGREC_LONG_TRANSACTION_ID data read(%d)\n"
"type %u, strid %u, len %u, i: %u, 4: %u 5: %u "
......@@ -498,7 +508,7 @@ int main(int argc, char *argv[])
lsn= rec.lsn;
len= translog_read_next_record_header(lsn_ptr, &rec, 1, &scanner);
len= translog_read_next_record_header(&scanner, &rec);
if ((rec_len= random() / (RAND_MAX / (LONG_BUFFER_SIZE + 1))) < 9)
rec_len= 9;
if (rec.type !=LOGREC_REDO_INSERT_ROW_HEAD ||
......
......@@ -42,10 +42,10 @@ static const char *default_dbug_option;
1 - Error
*/
static my_bool check_content(uchar *ptr, ulong length)
static my_bool check_content(byte *ptr, ulong length)
{
ulong i;
uchar buff[4];
byte buff[4];
DBUG_ENTER("check_content");
for (i= 0; i < length; i++)
{
......@@ -79,12 +79,12 @@ static my_bool check_content(uchar *ptr, ulong length)
*/
static my_bool read_and_check_content(TRANSLOG_HEADER_BUFFER *rec,
uchar *buffer, uint skip)
byte *buffer, uint skip)
{
int res= 0;
translog_size_t len;
DBUG_ENTER("read_and_check_content");
DBUG_ASSERT(rec->record_length < LONG_BUFFER_SIZE + 7 * 2 + 2);
DBUG_ASSERT(rec->record_length < LONG_BUFFER_SIZE + LSN_STORE_SIZE * 2 + 2);
if ((len= translog_read_record(rec->lsn, 0, rec->record_length,
buffer, NULL)) != rec->record_length)
{
......@@ -113,16 +113,16 @@ int main(int argc, char *argv[])
uint32 i;
uint32 rec_len;
uint pagen;
uchar long_tr_id[6];
uchar lsn_buff[23]=
byte long_tr_id[6];
byte lsn_buff[23]=
{
0x55, 0xAA, 0x55, 0xAA, 0x55, 0xAA, 0x55, 0xAA,
0x55, 0xAA, 0x55, 0xAA, 0x55, 0xAA, 0x55, 0xAA,
0x55, 0xAA, 0x55, 0xAA, 0x55, 0xAA, 0x55
};
uchar *long_buffer= malloc(LONG_BUFFER_SIZE + 7 * 2 + 2);
byte *long_buffer= malloc(LONG_BUFFER_SIZE + LSN_STORE_SIZE * 2 + 2);
PAGECACHE pagecache;
LSN lsn, lsn_base, first_lsn, lsn_ptr;
LSN lsn, lsn_base, first_lsn;
TRANSLOG_HEADER_BUFFER rec;
struct st_translog_scanner_data scanner;
int rc;
......@@ -133,8 +133,8 @@ int main(int argc, char *argv[])
maria_data_root= ".";
{
uchar buff[4];
for (i= 0; i < (LONG_BUFFER_SIZE + 7 * 2 + 2); i++)
byte buff[4];
for (i= 0; i < (LONG_BUFFER_SIZE + LSN_STORE_SIZE * 2 + 2); i++)
{
if (i % 4 == 0)
int4store(buff, (i >> 2));
......@@ -195,22 +195,24 @@ int main(int argc, char *argv[])
printf("write %d\n", i);
if (i % 2)
{
lsn7store(lsn_buff, lsn_base);
lsn_store(lsn_buff, lsn_base);
if (translog_write_record(&lsn,
LOGREC_CLR_END,
(i % 0xFFFF), NULL, 7, lsn_buff, 0))
(i % 0xFFFF), NULL,
LSN_STORE_SIZE, lsn_buff, 0))
{
fprintf(stderr, "1 Can't write reference before record #%lu\n",
(ulong) i);
translog_destroy();
exit(1);
}
lsn7store(lsn_buff, lsn_base);
lsn_store(lsn_buff, lsn_base);
rec_len= get_len();
if (translog_write_record(&lsn,
LOGREC_UNDO_KEY_INSERT,
(i % 0xFFFF),
NULL, 7, lsn_buff, rec_len, long_buffer, 0))
NULL, LSN_STORE_SIZE, lsn_buff,
rec_len, long_buffer, 0))
{
fprintf(stderr, "1 Can't write var reference before record #%lu\n",
(ulong) i);
......@@ -220,8 +222,8 @@ int main(int argc, char *argv[])
}
else
{
lsn7store(lsn_buff, lsn_base);
lsn7store(lsn_buff + 7, first_lsn);
lsn_store(lsn_buff, lsn_base);
lsn_store(lsn_buff + LSN_STORE_SIZE, first_lsn);
if (translog_write_record(&lsn,
LOGREC_UNDO_ROW_DELETE,
(i % 0xFFFF), NULL, 23, lsn_buff, 0))
......@@ -231,13 +233,14 @@ int main(int argc, char *argv[])
translog_destroy();
exit(1);
}
lsn7store(lsn_buff, lsn_base);
lsn7store(lsn_buff + 7, first_lsn);
lsn_store(lsn_buff, lsn_base);
lsn_store(lsn_buff + LSN_STORE_SIZE, first_lsn);
rec_len= get_len();
if (translog_write_record(&lsn,
LOGREC_UNDO_KEY_DELETE,
(i % 0xFFFF),
NULL, 14, lsn_buff, rec_len, long_buffer, 0))
NULL, LSN_STORE_SIZE * 2, lsn_buff,
rec_len, long_buffer, 0))
{
fprintf(stderr, "0 Can't write var reference before record #%lu\n",
(ulong) i);
......@@ -304,7 +307,7 @@ int main(int argc, char *argv[])
}
if (rec.type !=LOGREC_LONG_TRANSACTION_ID || rec.short_trid != 0 ||
rec.record_length != 6 || uint4korr(rec.header) != 0 ||
(uint)rec.header[4] != 0 || rec.header[5] != 0xFF ||
((uchar)rec.header[4]) != 0 || ((uchar)rec.header[5]) != 0xFF ||
first_lsn != rec.lsn)
{
fprintf(stderr, "Incorrect LOGREC_LONG_TRANSACTION_ID data read(0)\n"
......@@ -319,12 +322,16 @@ int main(int argc, char *argv[])
}
translog_free_record_header(&rec);
lsn= first_lsn;
lsn_ptr= first_lsn;
if (translog_init_scanner(first_lsn, 1, &scanner))
{
fprintf(stderr, "scanner init failed\n");
goto err;
}
for (i= 1;; i++)
{
if (i % SHOW_DIVIDER == 0)
printf("read %d\n", i);
len= translog_read_next_record_header(lsn_ptr, &rec, 1, &scanner);
len= translog_read_next_record_header(&scanner, &rec);
if (len == 0)
{
fprintf(stderr, "1-%d translog_read_next_record_header failed (%d)\n",
......@@ -343,15 +350,13 @@ int main(int argc, char *argv[])
}
break;
}
/* use scanner after its initialization */
lsn_ptr= 0;
if (i % 2)
{
LSN ref;
ref= lsn7korr(rec.header);
ref= lsn_korr(rec.header);
if (rec.type != LOGREC_CLR_END || rec.short_trid != (i % 0xFFFF) ||
rec.record_length != 7 || ref != lsn)
rec.record_length != LSN_STORE_SIZE || ref != lsn)
{
fprintf(stderr, "Incorrect LOGREC_CLR_END data read(%d)"
"type %u, strid %u, len %u, ref(%lu,0x%lx), lsn(%lu,0x%lx)\n",
......@@ -366,18 +371,22 @@ int main(int argc, char *argv[])
else
{
LSN ref1, ref2;
ref1= lsn7korr(rec.header);
ref2= lsn7korr(rec.header + 7);
ref1= lsn_korr(rec.header);
ref2= lsn_korr(rec.header + LSN_STORE_SIZE);
if (rec.type !=LOGREC_UNDO_ROW_DELETE ||
rec.short_trid != (i % 0xFFFF) ||
rec.record_length != 23 ||
ref1 != lsn ||
ref2 != first_lsn ||
rec.header[22] != 0x55 || rec.header[21] != 0xAA ||
rec.header[20] != 0x55 || rec.header[19] != 0xAA ||
rec.header[18] != 0x55 || rec.header[17] != 0xAA ||
rec.header[16] != 0x55 || rec.header[15] != 0xAA ||
rec.header[14] != 0x55)
((uchar)rec.header[22]) != 0x55 ||
((uchar)rec.header[21]) != 0xAA ||
((uchar)rec.header[20]) != 0x55 ||
((uchar)rec.header[19]) != 0xAA ||
((uchar)rec.header[18]) != 0x55 ||
((uchar)rec.header[17]) != 0xAA ||
((uchar)rec.header[16]) != 0x55 ||
((uchar)rec.header[15]) != 0xAA ||
((uchar)rec.header[14]) != 0x55)
{
fprintf(stderr, "Incorrect LOGREC_UNDO_ROW_DELETE data read(%d)"
"type %u, strid %u, len %u, ref1(%lu,0x%lx), "
......@@ -399,7 +408,7 @@ int main(int argc, char *argv[])
}
translog_free_record_header(&rec);
len= translog_read_next_record_header(lsn_ptr, &rec, 1, &scanner);
len= translog_read_next_record_header(&scanner, &rec);
if (len == 0)
{
fprintf(stderr, "1-%d translog_read_next_record_header (var) "
......@@ -415,13 +424,13 @@ int main(int argc, char *argv[])
if (i % 2)
{
LSN ref;
ref= lsn7korr(rec.header);
ref= lsn_korr(rec.header);
rec_len= get_len();
if (rec.type !=LOGREC_UNDO_KEY_INSERT ||
rec.short_trid != (i % 0xFFFF) ||
rec.record_length != rec_len + 7 ||
rec.record_length != rec_len + LSN_STORE_SIZE ||
len != 12 || ref != lsn ||
check_content(rec.header + 7, len - 7))
check_content(rec.header + LSN_STORE_SIZE, len - LSN_STORE_SIZE))
{
fprintf(stderr, "Incorrect LOGREC_UNDO_KEY_INSERT data read(%d)"
"type %u (%d), strid %u (%d), len %lu, %lu + 7 (%d), "
......@@ -432,17 +441,18 @@ int main(int argc, char *argv[])
(uint) rec.short_trid,
rec.short_trid != (i % 0xFFFF),
(ulong) rec.record_length, (ulong) rec_len,
rec.record_length != rec_len + 7,
rec.record_length != rec_len + LSN_STORE_SIZE,
(uint) len,
len != 12,
(ulong) LSN_FILE_NO(ref), (ulong) LSN_OFFSET(ref),
(ulong) LSN_FILE_NO(rec.lsn), (ulong) LSN_OFFSET(rec.lsn),
(ref != lsn),
check_content(rec.header + 7, len - 7));
check_content(rec.header + LSN_STORE_SIZE,
len - LSN_STORE_SIZE));
translog_free_record_header(&rec);
goto err;
}
if (read_and_check_content(&rec, long_buffer, 7))
if (read_and_check_content(&rec, long_buffer, LSN_STORE_SIZE))
{
fprintf(stderr,
"Incorrect LOGREC_UNDO_KEY_INSERT in whole rec read "
......@@ -455,19 +465,20 @@ int main(int argc, char *argv[])
else
{
LSN ref1, ref2;
ref1= lsn7korr(rec.header);
ref2= lsn7korr(rec.header + 7);
ref1= lsn_korr(rec.header);
ref2= lsn_korr(rec.header + LSN_STORE_SIZE);
rec_len= get_len();
if (rec.type !=LOGREC_UNDO_KEY_DELETE ||
rec.short_trid != (i % 0xFFFF) ||
rec.record_length != rec_len + 14 ||
rec.record_length != rec_len + LSN_STORE_SIZE * 2 ||
len != 19 ||
ref1 != lsn ||
ref2 != first_lsn ||
check_content(rec.header + 14, len - 14))
check_content(rec.header + LSN_STORE_SIZE * 2,
len - LSN_STORE_SIZE * 2))
{
fprintf(stderr, "Incorrect LOGREC_UNDO_KEY_DELETE data read(%d)"
"type %u, strid %u, len %lu != %lu + 7, hdr len: %u, "
"type %u, strid %u, len %lu != %lu + 14, hdr len: %u, "
"ref1(%lu,0x%lx), ref2(%lu,0x%lx), "
"lsn(%lu,0x%lx)\n",
i, (uint) rec.type, (uint) rec.short_trid,
......@@ -479,7 +490,7 @@ int main(int argc, char *argv[])
translog_free_record_header(&rec);
goto err;
}
if (read_and_check_content(&rec, long_buffer, 14))
if (read_and_check_content(&rec, long_buffer, LSN_STORE_SIZE * 2))
{
fprintf(stderr,
"Incorrect LOGREC_UNDO_KEY_DELETE in whole rec read "
......@@ -491,7 +502,7 @@ int main(int argc, char *argv[])
}
translog_free_record_header(&rec);
len= translog_read_next_record_header(lsn_ptr, &rec, 1, &scanner);
len= translog_read_next_record_header(&scanner, &rec);
if (len == 0)
{
fprintf(stderr, "1-%d translog_read_next_record_header failed (%d)\n",
......@@ -509,7 +520,7 @@ int main(int argc, char *argv[])
if (rec.type !=LOGREC_LONG_TRANSACTION_ID ||
rec.short_trid != (i % 0xFFFF) ||
rec.record_length != 6 || uint4korr(rec.header) != i ||
rec.header[4] != 0 || rec.header[5] != 0xFF)
((uchar)rec.header[4]) != 0 || ((uchar)rec.header[5]) != 0xFF)
{
fprintf(stderr, "Incorrect LOGREC_LONG_TRANSACTION_ID data read(%d)\n"
"type %u, strid %u, len %u, i: %u, 4: %u 5: %u "
......@@ -526,7 +537,7 @@ int main(int argc, char *argv[])
lsn= rec.lsn;
len= translog_read_next_record_header(lsn_ptr, &rec, 1, &scanner);
len= translog_read_next_record_header(&scanner, &rec);
rec_len= get_len();
if (rec.type !=LOGREC_REDO_INSERT_ROW_HEAD ||
rec.short_trid != (i % 0xFFFF) ||
......
......@@ -27,7 +27,7 @@ static uint thread_count;
static ulong lens[WRITERS][ITERATIONS];
static LSN lsns1[WRITERS][ITERATIONS];
static LSN lsns2[WRITERS][ITERATIONS];
static uchar *long_buffer;
static byte *long_buffer;
/*
Get pseudo-random length of the field in
......@@ -65,12 +65,12 @@ static uint32 get_len()
1 - Error
*/
static my_bool check_content(uchar *ptr, ulong length)
static my_bool check_content(byte *ptr, ulong length)
{
ulong i;
for (i= 0; i < length; i++)
{
if (ptr[i] != (i & 0xFF))
if (((uchar)ptr[i]) != (i & 0xFF))
{
fprintf(stderr, "Byte # %lu is %x instead of %x",
i, (uint) ptr[i], (uint) (i & 0xFF));
......@@ -97,7 +97,7 @@ static my_bool check_content(uchar *ptr, ulong length)
static my_bool read_and_check_content(TRANSLOG_HEADER_BUFFER *rec,
uchar *buffer, uint skip)
byte *buffer, uint skip)
{
int res= 0;
translog_size_t len;
......@@ -117,7 +117,7 @@ static my_bool read_and_check_content(TRANSLOG_HEADER_BUFFER *rec,
void writer(int num)
{
LSN lsn;
uchar long_tr_id[6];
byte long_tr_id[6];
uint i;
DBUG_ENTER("writer");
......@@ -193,7 +193,7 @@ int main(int argc, char **argv __attribute__ ((unused)))
uint32 i;
uint pagen;
PAGECACHE pagecache;
LSN first_lsn, lsn_ptr;
LSN first_lsn;
TRANSLOG_HEADER_BUFFER rec;
struct st_translog_scanner_data scanner;
pthread_t tid;
......@@ -290,7 +290,7 @@ int main(int argc, char **argv __attribute__ ((unused)))
srandom(122334817L);
{
uchar long_tr_id[6]=
byte long_tr_id[6]=
{
0x11, 0x22, 0x33, 0x44, 0x55, 0x66
};
......@@ -369,11 +369,14 @@ int main(int argc, char **argv __attribute__ ((unused)))
bzero(indeces, sizeof(indeces));
lsn_ptr= first_lsn;
if (translog_init_scanner(first_lsn, 1, &scanner))
{
fprintf(stderr, "scanner init failed\n");
goto err;
}
for (i= 0;; i++)
{
len= translog_read_next_record_header(lsn_ptr, &rec, 1, &scanner);
lsn_ptr= 0;
len= translog_read_next_record_header(&scanner, &rec);
if (len == 0)
{
......
......@@ -107,7 +107,7 @@ int main(int argc, char *argv[])
bzero(page, PCACHE_PAGE);
#define PAGE_LSN_OFFSET 0
lsn7store(page + PAGE_LSN_OFFSET, lsn);
lsn_store(page + PAGE_LSN_OFFSET, lsn);
pagecache_write(&pagecache, &file1, 0, 3, (char*)page,
PAGECACHE_LSN_PAGE,
PAGECACHE_LOCK_LEFT_UNLOCKED,
......
......@@ -17,3 +17,10 @@
0 belong&0xffffff00 0xfefe0600 MySQL ISAM compressed data file
>3 byte x Version %d
0 string \376bin MySQL replication log
0 belong&0xffffff00 0xfefe0b00
>4 string MARIALOG MySQL Maria transaction log file
>>3 byte x Version %d
0 belong&0xffffff00 0xfefe0c00
>4 string MACF MySQL Maria control file
>>3 byte x Version %d
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