Commit 8edb454a authored by unknown's avatar unknown

fix for bug in Solaris 10 Sparc 64 bit (misaligned buffer in the

log handler).


storage/maria/ma_loghandler.c:
  Buffers on the stack must be properly aligned as pagecache_read()
  will use bmove512() on them. Fixes hang in maria-recovery.test
  on Solaris 10 Sparc 64 bit.
storage/maria/ma_pagecache.c:
  comment
parent 6c964d7e
...@@ -57,6 +57,16 @@ typedef struct st_translog_file ...@@ -57,6 +57,16 @@ typedef struct st_translog_file
/* records buffer size (should be TRANSLOG_PAGE_SIZE * n) */ /* records buffer size (should be TRANSLOG_PAGE_SIZE * n) */
#define TRANSLOG_WRITE_BUFFER (1024*1024) #define TRANSLOG_WRITE_BUFFER (1024*1024)
/*
pagecache_read/write/inject() use bmove512() on their buffers so those must
be long-aligned, which we guarantee by using the type below:
*/
typedef union
{
ulonglong dummy;
uchar buffer[TRANSLOG_PAGE_SIZE];
} TRANSLOG_PAGE_SIZE_BUFF;
/* min chunk length */ /* min chunk length */
#define TRANSLOG_MIN_CHUNK 3 #define TRANSLOG_MIN_CHUNK 3
/* /*
...@@ -3501,9 +3511,10 @@ my_bool translog_init_with_table(const char *directory, ...@@ -3501,9 +3511,10 @@ my_bool translog_init_with_table(const char *directory,
do do
{ {
TRANSLOG_VALIDATOR_DATA data; TRANSLOG_VALIDATOR_DATA data;
uchar buffer[TRANSLOG_PAGE_SIZE], *page; TRANSLOG_PAGE_SIZE_BUFF psize_buff;
uchar *page;
data.addr= &current_page; data.addr= &current_page;
if ((page= translog_get_page(&data, buffer, NULL)) == NULL) if ((page= translog_get_page(&data, psize_buff.buffer, NULL)) == NULL)
DBUG_RETURN(1); DBUG_RETURN(1);
if (data.was_recovered) if (data.was_recovered)
{ {
...@@ -3549,13 +3560,14 @@ my_bool translog_init_with_table(const char *directory, ...@@ -3549,13 +3560,14 @@ my_bool translog_init_with_table(const char *directory,
if (logs_found && !old_log_was_recovered && old_flags == flags) if (logs_found && !old_log_was_recovered && old_flags == flags)
{ {
TRANSLOG_VALIDATOR_DATA data; TRANSLOG_VALIDATOR_DATA data;
uchar buffer[TRANSLOG_PAGE_SIZE], *page; TRANSLOG_PAGE_SIZE_BUFF psize_buff;
uchar *page;
uint16 chunk_offset; uint16 chunk_offset;
data.addr= &last_valid_page; data.addr= &last_valid_page;
/* continue old log */ /* continue old log */
DBUG_ASSERT(LSN_FILE_NO(last_valid_page)== DBUG_ASSERT(LSN_FILE_NO(last_valid_page)==
LSN_FILE_NO(log_descriptor.horizon)); LSN_FILE_NO(log_descriptor.horizon));
if ((page= translog_get_page(&data, buffer, NULL)) == NULL || if ((page= translog_get_page(&data, psize_buff.buffer, NULL)) == NULL ||
(chunk_offset= translog_get_first_chunk_offset(page)) == 0) (chunk_offset= translog_get_first_chunk_offset(page)) == 0)
DBUG_RETURN(1); DBUG_RETURN(1);
...@@ -6644,7 +6656,8 @@ int translog_read_record_header_from_buffer(uchar *page, ...@@ -6644,7 +6656,8 @@ int translog_read_record_header_from_buffer(uchar *page,
int translog_read_record_header(LSN lsn, TRANSLOG_HEADER_BUFFER *buff) int translog_read_record_header(LSN lsn, TRANSLOG_HEADER_BUFFER *buff)
{ {
uchar buffer[TRANSLOG_PAGE_SIZE], *page; TRANSLOG_PAGE_SIZE_BUFF psize_buff;
uchar *page;
translog_size_t res, page_offset= LSN_OFFSET(lsn) % TRANSLOG_PAGE_SIZE; translog_size_t res, page_offset= LSN_OFFSET(lsn) % TRANSLOG_PAGE_SIZE;
PAGECACHE_BLOCK_LINK *direct_link; PAGECACHE_BLOCK_LINK *direct_link;
TRANSLOG_ADDRESS addr; TRANSLOG_ADDRESS addr;
...@@ -6661,7 +6674,7 @@ int translog_read_record_header(LSN lsn, TRANSLOG_HEADER_BUFFER *buff) ...@@ -6661,7 +6674,7 @@ int translog_read_record_header(LSN lsn, TRANSLOG_HEADER_BUFFER *buff)
data.was_recovered= 0; data.was_recovered= 0;
addr= lsn; addr= lsn;
addr-= page_offset; /* offset decreasing */ addr-= page_offset; /* offset decreasing */
res= (!(page= translog_get_page(&data, buffer, &direct_link))) ? res= (!(page= translog_get_page(&data, psize_buff.buffer, &direct_link))) ?
RECHEADER_READ_ERROR : RECHEADER_READ_ERROR :
translog_read_record_header_from_buffer(page, page_offset, buff, 0); translog_read_record_header_from_buffer(page, page_offset, buff, 0);
translog_free_link(direct_link); translog_free_link(direct_link);
...@@ -7697,8 +7710,8 @@ LSN translog_first_lsn_in_log() ...@@ -7697,8 +7710,8 @@ LSN translog_first_lsn_in_log()
addr= MAKE_LSN(file, TRANSLOG_PAGE_SIZE); /* the first page of the file */ addr= MAKE_LSN(file, TRANSLOG_PAGE_SIZE); /* the first page of the file */
data.addr= &addr; data.addr= &addr;
{ {
uchar buffer[TRANSLOG_PAGE_SIZE]; TRANSLOG_PAGE_SIZE_BUFF psize_buff;
if ((page= translog_get_page(&data, buffer, NULL)) == NULL || if ((page= translog_get_page(&data, psize_buff.buffer, NULL)) == NULL ||
(chunk_offset= translog_get_first_chunk_offset(page)) == 0) (chunk_offset= translog_get_first_chunk_offset(page)) == 0)
DBUG_RETURN(LSN_ERROR); DBUG_RETURN(LSN_ERROR);
} }
...@@ -7719,7 +7732,8 @@ LSN translog_first_lsn_in_log() ...@@ -7719,7 +7732,8 @@ LSN translog_first_lsn_in_log()
LSN translog_first_theoretical_lsn() LSN translog_first_theoretical_lsn()
{ {
TRANSLOG_ADDRESS addr= translog_get_horizon(); TRANSLOG_ADDRESS addr= translog_get_horizon();
uchar buffer[TRANSLOG_PAGE_SIZE], *page; TRANSLOG_PAGE_SIZE_BUFF psize_buff;
uchar *page;
TRANSLOG_VALIDATOR_DATA data; TRANSLOG_VALIDATOR_DATA data;
DBUG_ENTER("translog_first_theoretical_lsn"); DBUG_ENTER("translog_first_theoretical_lsn");
DBUG_PRINT("info", ("Horizon: (%lu,0x%lx)", LSN_IN_PARTS(addr))); DBUG_PRINT("info", ("Horizon: (%lu,0x%lx)", LSN_IN_PARTS(addr)));
...@@ -7737,7 +7751,7 @@ LSN translog_first_theoretical_lsn() ...@@ -7737,7 +7751,7 @@ LSN translog_first_theoretical_lsn()
addr= MAKE_LSN(1, TRANSLOG_PAGE_SIZE); /* the first page of the file */ addr= MAKE_LSN(1, TRANSLOG_PAGE_SIZE); /* the first page of the file */
data.addr= &addr; data.addr= &addr;
if ((page= translog_get_page(&data, buffer, NULL)) == NULL) if ((page= translog_get_page(&data, psize_buff.buffer, NULL)) == NULL)
DBUG_RETURN(LSN_ERROR); DBUG_RETURN(LSN_ERROR);
DBUG_RETURN(MAKE_LSN(1, TRANSLOG_PAGE_SIZE + DBUG_RETURN(MAKE_LSN(1, TRANSLOG_PAGE_SIZE +
......
...@@ -2949,6 +2949,11 @@ static enum pagecache_page_pin lock_to_pin[2][8]= ...@@ -2949,6 +2949,11 @@ static enum pagecache_page_pin lock_to_pin[2][8]=
} }
}; };
/**
@note 'buff', if not NULL, must be long-aligned.
*/
uchar *pagecache_read(PAGECACHE *pagecache, uchar *pagecache_read(PAGECACHE *pagecache,
PAGECACHE_FILE *file, PAGECACHE_FILE *file,
pgcache_page_no_t pageno, pgcache_page_no_t pageno,
...@@ -3460,6 +3465,11 @@ static struct write_pin_change write_pin_change_table[]= ...@@ -3460,6 +3465,11 @@ static struct write_pin_change write_pin_change_table[]=
PAGECACHE_UNPIN} /*PAGECACHE_UNPIN*/ PAGECACHE_UNPIN} /*PAGECACHE_UNPIN*/
}; };
/**
@note 'buff', if not NULL, must be long-aligned.
*/
my_bool pagecache_write_part(PAGECACHE *pagecache, my_bool pagecache_write_part(PAGECACHE *pagecache,
PAGECACHE_FILE *file, PAGECACHE_FILE *file,
pgcache_page_no_t pageno, pgcache_page_no_t pageno,
......
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