mirror of
https://github.com/MariaDB/server.git
synced 2025-01-29 10:14:19 +01:00
removing old file replaced by ma_key_recover.c
BitKeeper/deleted/.del-ma_key_redo.c: Delete: storage/maria/ma_key_redo.c storage/maria/ma_recovery.c: now that we have indices, when state is older we don't always update rows' count
This commit is contained in:
parent
63cd7bdcd5
commit
3c3d518c88
2 changed files with 2 additions and 419 deletions
|
@ -1,417 +0,0 @@
|
|||
/* Copyright (C) 2007 Michael Widenius
|
||||
|
||||
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 */
|
||||
|
||||
/* Redo of index */
|
||||
|
||||
#include "maria_def.h"
|
||||
#include "ma_blockrec.h"
|
||||
#include "trnman.h"
|
||||
|
||||
/**
|
||||
@brief Apply LOGREC_REDO_INDEX_NEW_PAGE
|
||||
|
||||
@param info Maria handler
|
||||
@param header Header (without FILEID)
|
||||
|
||||
@return Operation status
|
||||
@retval 0 OK
|
||||
@retval 1 Error
|
||||
*/
|
||||
|
||||
uint _ma_apply_redo_index_new_page(MARIA_HA *info, LSN lsn,
|
||||
const uchar *header, uint length)
|
||||
{
|
||||
ulonglong root_page= page_korr(header);
|
||||
ulonglong free_page= page_korr(header + PAGE_STORE_SIZE);
|
||||
enum pagecache_page_lock unlock_method;
|
||||
enum pagecache_page_pin unpin_method;
|
||||
MARIA_PINNED_PAGE page_link;
|
||||
my_off_t file_size;
|
||||
uchar *buff;
|
||||
uint result;
|
||||
DBUG_ENTER("_ma_apply_redo_index_new_page");
|
||||
|
||||
/* Set header to point at key data */
|
||||
header+= PAGE_STORE_SIZE*2;
|
||||
length-= PAGE_STORE_SIZE*2;
|
||||
|
||||
if (free_page != IMPOSSIBLE_PAGE_NO)
|
||||
info->s->state.key_del= (my_off_t) free_page * info->s->block_size;
|
||||
else
|
||||
info->s->state.key_del= HA_OFFSET_ERROR;
|
||||
|
||||
file_size= (my_off_t) (root_page + 1) * info->s->block_size;
|
||||
if (file_size > info->state->key_file_length)
|
||||
{
|
||||
info->state->key_file_length= file_size;
|
||||
buff= info->keyread_buff;
|
||||
info->keyread_buff_used= 1;
|
||||
unlock_method= PAGECACHE_LOCK_LEFT_UNLOCKED;
|
||||
unpin_method= PAGECACHE_PIN_LEFT_UNPINNED;
|
||||
}
|
||||
else
|
||||
{
|
||||
if (!(buff= pagecache_read(info->s->pagecache, &info->dfile,
|
||||
root_page, 0, 0,
|
||||
PAGECACHE_PLAIN_PAGE, PAGECACHE_LOCK_WRITE,
|
||||
&page_link.link)))
|
||||
{
|
||||
result= (uint) my_errno;
|
||||
goto err;
|
||||
}
|
||||
if (lsn_korr(buff) >= lsn)
|
||||
{
|
||||
/* Already applied */
|
||||
result= 0;
|
||||
goto err;
|
||||
}
|
||||
unlock_method= PAGECACHE_LOCK_WRITE_UNLOCK;
|
||||
unpin_method= PAGECACHE_UNPIN;
|
||||
}
|
||||
|
||||
/* Write modified page */
|
||||
lsn_store(buff, lsn);
|
||||
memcpy(buff + LSN_STORE_SIZE, header, length);
|
||||
#ifdef IDENTICAL_PAGES_AFTER_RECOVERY
|
||||
bzero(buff + LSN_STORE_SIZE + length,
|
||||
info->s->block_size - LSN_STORE_SIZE - length);
|
||||
#endif
|
||||
if (pagecache_write(info->s->pagecache,
|
||||
&info->dfile, root_page, 0,
|
||||
buff, PAGECACHE_PLAIN_PAGE,
|
||||
unlock_method, unpin_method,
|
||||
PAGECACHE_WRITE_DELAY, 0))
|
||||
DBUG_RETURN(my_errno);
|
||||
DBUG_RETURN(0);
|
||||
|
||||
err:
|
||||
pagecache_unlock_by_link(info->s->pagecache, page_link.link,
|
||||
PAGECACHE_LOCK_WRITE_UNLOCK,
|
||||
PAGECACHE_UNPIN, LSN_IMPOSSIBLE,
|
||||
LSN_IMPOSSIBLE);
|
||||
DBUG_RETURN(result);
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
@brief Apply LOGREC_REDO_INDEX_FREE_PAGE
|
||||
|
||||
@param info Maria handler
|
||||
@param header Header (without FILEID)
|
||||
|
||||
@return Operation status
|
||||
@retval 0 OK
|
||||
@retval 1 Error
|
||||
*/
|
||||
|
||||
uint _ma_apply_redo_index_free_page(MARIA_HA *info,
|
||||
LSN lsn,
|
||||
const uchar *header)
|
||||
{
|
||||
ulonglong page= page_korr(header);
|
||||
ulonglong free_page= page_korr(header + PAGE_STORE_SIZE);
|
||||
my_off_t old_link;
|
||||
MARIA_PINNED_PAGE page_link;
|
||||
MARIA_SHARE *share= info->s;
|
||||
uchar *buff;
|
||||
int result;
|
||||
DBUG_ENTER("_ma_apply_redo_index_free_page");
|
||||
|
||||
old_link= share->state.key_del;
|
||||
share->state.key_del= ((free_page != IMPOSSIBLE_PAGE_NO) ?
|
||||
(my_off_t) free_page * share->block_size :
|
||||
HA_OFFSET_ERROR);
|
||||
if (!(buff= pagecache_read(share->pagecache, &info->dfile,
|
||||
page, 0, 0,
|
||||
PAGECACHE_PLAIN_PAGE, PAGECACHE_LOCK_WRITE,
|
||||
&page_link.link)))
|
||||
{
|
||||
result= (uint) my_errno;
|
||||
goto err;
|
||||
}
|
||||
if (lsn_korr(buff) >= lsn)
|
||||
{
|
||||
/* Already applied */
|
||||
result= 0;
|
||||
goto err;
|
||||
}
|
||||
/* Write modified page */
|
||||
lsn_store(buff, lsn);
|
||||
bzero(buff + LSN_STORE_SIZE, share->keypage_header - LSN_STORE_SIZE);
|
||||
_ma_store_keynr(info, buff, (uchar) MARIA_DELETE_KEY_NR);
|
||||
mi_sizestore(buff + share->keypage_header, old_link);
|
||||
share->state.changed|= STATE_NOT_SORTED_PAGES;
|
||||
|
||||
if (pagecache_write(share->pagecache,
|
||||
&info->dfile, page, 0,
|
||||
buff, PAGECACHE_PLAIN_PAGE,
|
||||
PAGECACHE_LOCK_WRITE_UNLOCK,
|
||||
PAGECACHE_UNPIN,
|
||||
PAGECACHE_WRITE_DELAY, 0))
|
||||
DBUG_RETURN(my_errno);
|
||||
DBUG_RETURN(0);
|
||||
|
||||
err:
|
||||
pagecache_unlock_by_link(share->pagecache, page_link.link,
|
||||
PAGECACHE_LOCK_WRITE_UNLOCK,
|
||||
PAGECACHE_UNPIN, LSN_IMPOSSIBLE,
|
||||
LSN_IMPOSSIBLE);
|
||||
DBUG_RETURN(result);
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
@brief Apply LOGREC_REDO_INDEX
|
||||
|
||||
@fn ma_apply_redo_index()
|
||||
@param info Maria handler
|
||||
@param header Header (without FILEID)
|
||||
|
||||
@notes
|
||||
Data for this part is a set of logical instructions of how to
|
||||
construct the key page.
|
||||
|
||||
Information of the layout of the components for REDO_INDEX:
|
||||
|
||||
Name Parameters (in byte) Information
|
||||
KEY_OP_OFFSET 2 Set position for next operations
|
||||
KEY_OP_SHIFT 2 (signed int) How much to shift down or up
|
||||
KEY_OP_CHANGE 2 length, data Data to replace at 'pos'
|
||||
KEY_OP_ADD_PREFIX 2 move-length How much data should be moved up
|
||||
2 change-length Data to be replaced at page start
|
||||
KEY_OP_DEL_PREFIX 2 length Bytes to be deleted at page start
|
||||
KEY_OP_ADD_SUFFIX 2 length, data Add data to end of page
|
||||
KEY_OP_DEL_SUFFIX 2 length Reduce page length with this
|
||||
|
||||
@return Operation status
|
||||
@retval 0 OK
|
||||
@retval 1 Error
|
||||
*/
|
||||
|
||||
uint _ma_apply_redo_index(MARIA_HA *info,
|
||||
LSN lsn, const uchar *header, uint length)
|
||||
{
|
||||
ulonglong root_page= page_korr(header);
|
||||
MARIA_PINNED_PAGE page_link;
|
||||
uchar *buff;
|
||||
const uchar *header_end= header + length;
|
||||
uint page_offset= 0;
|
||||
uint nod_flag, page_length, keypage_header;
|
||||
int result;
|
||||
DBUG_ENTER("_ma_apply_redo_index");
|
||||
|
||||
/* Set header to point at key data */
|
||||
header+= PAGE_STORE_SIZE;
|
||||
|
||||
if (!(buff= pagecache_read(info->s->pagecache, &info->dfile,
|
||||
root_page, 0, 0,
|
||||
PAGECACHE_PLAIN_PAGE, PAGECACHE_LOCK_WRITE,
|
||||
&page_link.link)))
|
||||
{
|
||||
result= (uint) my_errno;
|
||||
goto err;
|
||||
}
|
||||
if (lsn_korr(buff) >= lsn)
|
||||
{
|
||||
/* Already applied */
|
||||
result= 0;
|
||||
goto err;
|
||||
}
|
||||
|
||||
_ma_get_used_and_nod(info, buff, page_length, nod_flag);
|
||||
keypage_header= info->s->keypage_header;
|
||||
|
||||
/* Apply modifications to page */
|
||||
do
|
||||
{
|
||||
switch ((enum en_key_op) (*header++)) {
|
||||
case KEY_OP_NONE:
|
||||
DBUG_ASSERT(0); /* Impossible */
|
||||
break;
|
||||
case KEY_OP_OFFSET:
|
||||
page_offset= uint2korr(header);
|
||||
header+= 2;
|
||||
DBUG_ASSERT(page_offset >= keypage_header && page_offset <= page_length);
|
||||
break;
|
||||
case KEY_OP_SHIFT:
|
||||
{
|
||||
int length= sint2korr(header);
|
||||
header+= 2;
|
||||
DBUG_ASSERT(page_offset != 0 && page_offset < page_length &&
|
||||
page_length + length < info->s->block_size);
|
||||
|
||||
if (length < 0)
|
||||
bmove(buff + page_offset, buff + page_offset - length,
|
||||
page_length - page_offset + length);
|
||||
else
|
||||
bmove_upp(buff + page_length + length, buff + page_length,
|
||||
page_length - page_offset);
|
||||
page_length+= length;
|
||||
break;
|
||||
}
|
||||
case KEY_OP_CHANGE:
|
||||
{
|
||||
uint length= uint2korr(header);
|
||||
DBUG_ASSERT(page_offset != 0 && page_offset + length <= page_length);
|
||||
|
||||
memcpy(buff + page_offset, header + 2 , length);
|
||||
header+= 2 + length;
|
||||
break;
|
||||
}
|
||||
case KEY_OP_ADD_PREFIX:
|
||||
{
|
||||
uint insert_length= uint2korr(header);
|
||||
uint change_length= uint2korr(header+2);
|
||||
DBUG_ASSERT(insert_length <= change_length &&
|
||||
page_length + change_length < info->s->block_size);
|
||||
|
||||
bmove_upp(buff + page_length + insert_length, buff + page_length,
|
||||
page_length - keypage_header);
|
||||
memcpy(buff + keypage_header, header + 2 , change_length);
|
||||
header+= 4 + change_length;
|
||||
page_length+= insert_length;
|
||||
break;
|
||||
}
|
||||
case KEY_OP_DEL_PREFIX:
|
||||
{
|
||||
uint length= uint2korr(header);
|
||||
header+= 2;
|
||||
DBUG_ASSERT(length <= page_length - keypage_header);
|
||||
|
||||
bmove(buff + keypage_header, buff + keypage_header +
|
||||
length, page_length - keypage_header - length);
|
||||
page_length-= length;
|
||||
break;
|
||||
}
|
||||
case KEY_OP_ADD_SUFFIX:
|
||||
{
|
||||
uint insert_length= uint2korr(header);
|
||||
DBUG_ASSERT(page_length + insert_length < info->s->block_size);
|
||||
memcpy(buff + page_length, header, insert_length);
|
||||
page_length= insert_length;
|
||||
header+= 2 + insert_length;
|
||||
break;
|
||||
}
|
||||
case KEY_OP_DEL_SUFFIX:
|
||||
{
|
||||
uint del_length= uint2korr(header);
|
||||
header+= 2;
|
||||
DBUG_ASSERT(page_length - del_length >= keypage_header);
|
||||
page_length-= del_length;
|
||||
break;
|
||||
}
|
||||
}
|
||||
} while (header < header_end);
|
||||
DBUG_ASSERT(header == header_end);
|
||||
|
||||
/* Write modified page */
|
||||
lsn_store(buff, lsn);
|
||||
memcpy(buff + LSN_STORE_SIZE, header, length);
|
||||
_ma_store_page_used(info, buff, page_length, nod_flag);
|
||||
|
||||
if (pagecache_write(info->s->pagecache,
|
||||
&info->dfile, root_page, 0,
|
||||
buff, PAGECACHE_PLAIN_PAGE,
|
||||
PAGECACHE_LOCK_WRITE_UNLOCK, PAGECACHE_UNPIN,
|
||||
PAGECACHE_WRITE_DELAY, 0))
|
||||
DBUG_RETURN(my_errno);
|
||||
DBUG_RETURN(0);
|
||||
|
||||
err:
|
||||
pagecache_unlock_by_link(info->s->pagecache, page_link.link,
|
||||
PAGECACHE_LOCK_WRITE_UNLOCK,
|
||||
PAGECACHE_UNPIN, LSN_IMPOSSIBLE,
|
||||
LSN_IMPOSSIBLE);
|
||||
DBUG_RETURN(result);
|
||||
}
|
||||
|
||||
/*
|
||||
Unpin all pinned pages
|
||||
|
||||
SYNOPSIS
|
||||
_ma_unpin_all_pages()
|
||||
info Maria handler
|
||||
undo_lsn LSN for undo pages. LSN_IMPOSSIBLE if we shouldn't write undo
|
||||
(error)
|
||||
|
||||
NOTE
|
||||
We unpin pages in the reverse order as they where pinned; This may not
|
||||
be strictly necessary but may simplify things in the future.
|
||||
|
||||
RETURN
|
||||
0 ok
|
||||
1 error (fatal disk error)
|
||||
|
||||
*/
|
||||
|
||||
void _ma_unpin_all_pages(MARIA_HA *info, LSN undo_lsn)
|
||||
{
|
||||
MARIA_PINNED_PAGE *page_link= ((MARIA_PINNED_PAGE*)
|
||||
dynamic_array_ptr(&info->pinned_pages, 0));
|
||||
MARIA_PINNED_PAGE *pinned_page= page_link + info->pinned_pages.elements;
|
||||
DBUG_ENTER("_ma_unpin_all_pages");
|
||||
DBUG_PRINT("info", ("undo_lsn: %lu", (ulong) undo_lsn));
|
||||
|
||||
if (!info->s->now_transactional)
|
||||
undo_lsn= LSN_IMPOSSIBLE; /* don't try to set a LSN on pages */
|
||||
|
||||
while (pinned_page-- != page_link)
|
||||
{
|
||||
DBUG_ASSERT(pinned_page->changed &&
|
||||
((undo_lsn != LSN_IMPOSSIBLE) || !info->s->now_transactional));
|
||||
pagecache_unlock_by_link(info->s->pagecache, pinned_page->link,
|
||||
pinned_page->unlock, PAGECACHE_UNPIN,
|
||||
info->trn->rec_lsn, undo_lsn);
|
||||
}
|
||||
|
||||
info->pinned_pages.elements= 0;
|
||||
DBUG_VOID_RETURN;
|
||||
}
|
||||
|
||||
|
||||
/****************************************************************************
|
||||
Undo of key block changes
|
||||
****************************************************************************/
|
||||
|
||||
|
||||
/*
|
||||
Undo of insert of key (ie, delete the inserted key)
|
||||
*/
|
||||
|
||||
my_bool _ma_apply_undo_key_insert(MARIA_HA *info, LSN undo_lsn,
|
||||
const uchar *header, uint length)
|
||||
{
|
||||
ulonglong page;
|
||||
uint rownr;
|
||||
LEX_STRING log_array[TRANSLOG_INTERNAL_PARTS + 1];
|
||||
uchar log_data[LSN_STORE_SIZE + FILEID_STORE_SIZE +
|
||||
CLR_TYPE_STORE_SIZE + HA_CHECKSUM_STORE_SIZE],
|
||||
*buff;
|
||||
my_bool res= 1;
|
||||
MARIA_PINNED_PAGE page_link;
|
||||
LSN lsn= LSN_IMPOSSIBLE;
|
||||
MARIA_SHARE *share= info->s;
|
||||
struct st_msg_to_write_hook_for_clr_end msg;
|
||||
DBUG_ENTER("_ma_apply_undo_key_insert");
|
||||
|
||||
keynr= keynr_korr(header);
|
||||
key= header+ KEY_NR_STORE_SIZE;
|
||||
length-= KEYNR_STORE_SIZE;
|
||||
|
||||
res= _ma_ck_delete(info, info->s->keyinfo+keynr, key, length,
|
||||
&info->s->state.key_root[keynr]);
|
||||
_ma_unpin_all_pages_and_finalize_row(info, lsn);
|
||||
DBUG_RETURN(res);
|
||||
}
|
|
@ -1522,7 +1522,7 @@ prototype_redo_exec_hook(UNDO_ROW_DELETE)
|
|||
set_undo_lsn_for_active_trans(rec->short_trid, rec->lsn);
|
||||
if (cmp_translog_addr(rec->lsn, share->state.is_of_horizon) >= 0)
|
||||
{
|
||||
tprint(tracef, " state older than record, updating rows' count\n");
|
||||
tprint(tracef, " state older than record\n");
|
||||
share->state.state.records--;
|
||||
if (share->calc_checksum)
|
||||
{
|
||||
|
@ -1683,7 +1683,7 @@ prototype_redo_exec_hook(CLR_END)
|
|||
log_desc->name, LSN_IN_PARTS(previous_undo_lsn));
|
||||
if (cmp_translog_addr(rec->lsn, share->state.is_of_horizon) >= 0)
|
||||
{
|
||||
tprint(tracef, " state older than record, updating rows' count\n");
|
||||
tprint(tracef, " state older than record\n");
|
||||
switch (undone_record_type) {
|
||||
case LOGREC_UNDO_ROW_DELETE:
|
||||
row_entry= 1;
|
||||
|
|
Loading…
Add table
Reference in a new issue