diff options
author | Michael Widenius <monty@askmonty.org> | 2011-01-05 16:03:58 +0200 |
---|---|---|
committer | Michael Widenius <monty@askmonty.org> | 2011-01-05 16:03:58 +0200 |
commit | 215043b7c2ace7ce05dcf6c685c87a293ccf1cd7 (patch) | |
tree | 679d57ddbf9713b7129872db144ff408b0215b31 /storage | |
parent | 31a78529bc5c4431865eba06762e6cc66359f759 (diff) | |
parent | 6b03fbf9fcacc74cb2999ba7715d22d754f356c7 (diff) | |
download | mariadb-git-215043b7c2ace7ce05dcf6c685c87a293ccf1cd7.tar.gz |
Merge with 5.1
Diffstat (limited to 'storage')
-rw-r--r-- | storage/maria/ma_bitmap.c | 6 | ||||
-rw-r--r-- | storage/maria/ma_blockrec.c | 62 | ||||
-rw-r--r-- | storage/maria/ma_blockrec.h | 2 | ||||
-rw-r--r-- | storage/maria/ma_check.c | 63 | ||||
-rw-r--r-- | storage/maria/ma_recovery.c | 9 |
5 files changed, 109 insertions, 33 deletions
diff --git a/storage/maria/ma_bitmap.c b/storage/maria/ma_bitmap.c index 7e68437de2b..bc83f6ea0e9 100644 --- a/storage/maria/ma_bitmap.c +++ b/storage/maria/ma_bitmap.c @@ -399,7 +399,8 @@ my_bool _ma_bitmap_flush_all(MARIA_SHARE *share) become false, wake them up. */ DBUG_PRINT("info", ("bitmap flusher waking up others")); - pthread_cond_broadcast(&bitmap->bitmap_cond); + if (bitmap->flush_all_requested) + pthread_cond_broadcast(&bitmap->bitmap_cond); } pthread_mutex_unlock(&bitmap->bitmap_lock); DBUG_RETURN(res); @@ -465,7 +466,8 @@ void _ma_bitmap_unlock(MARIA_SHARE *share) bitmap->flush_all_requested--; bitmap->non_flushable= 0; pthread_mutex_unlock(&bitmap->bitmap_lock); - pthread_cond_broadcast(&bitmap->bitmap_cond); + if (bitmap->flush_all_requested > 0) + pthread_cond_broadcast(&bitmap->bitmap_cond); DBUG_VOID_RETURN; } diff --git a/storage/maria/ma_blockrec.c b/storage/maria/ma_blockrec.c index fd02e2ac0ec..dab88287f86 100644 --- a/storage/maria/ma_blockrec.c +++ b/storage/maria/ma_blockrec.c @@ -2506,7 +2506,7 @@ static my_bool free_full_page_range(MARIA_HA *info, pgcache_page_no_t page, } if (delete_count && pagecache_delete_pages(share->pagecache, &info->dfile, - page, delete_count, PAGECACHE_LOCK_WRITE, 0)) + page, delete_count, PAGECACHE_LOCK_WRITE, 1)) res= 1; if (share->now_transactional) @@ -2816,7 +2816,6 @@ static my_bool write_block_record(MARIA_HA *info, DBUG_PRINT("info", ("Used head length on page: %u header_length: %u", head_length, (uint) (flag & ROW_FLAG_TRANSID ? TRANSID_SIZE : 0))); - DBUG_ASSERT(data <= end_of_data); if (head_length < share->base.min_block_length) { /* Extend row to be of size min_block_length */ @@ -2825,6 +2824,7 @@ static my_bool write_block_record(MARIA_HA *info, data+= diff_length; head_length= share->base.min_block_length; } + DBUG_ASSERT(data <= end_of_data); /* If this is a redo entry (ie, undo_lsn != LSN_ERROR) then we should have written exactly head_length bytes (same as original record). @@ -3492,7 +3492,9 @@ static my_bool allocate_and_write_block_record(MARIA_HA *info, /* page will be pinned & locked by get_head_or_tail_page */ if (get_head_or_tail_page(info, blocks->block, info->buff, - row->space_on_head_page, HEAD_PAGE, + max(row->space_on_head_page, + info->s->base.min_block_length), + HEAD_PAGE, PAGECACHE_LOCK_WRITE, &row_pos)) goto err; row->lastpos= ma_recordpos(blocks->block->page, row_pos.rownr); @@ -6485,7 +6487,13 @@ err: @param info Maria handler @param header Header (without FILEID) - @note It marks the pages free in the bitmap + Mark the pages free in the bitmap. + + We have to check against _ma_redo_not_needed_for_page() + to guard against the case where we first clear a block and after + that insert new data into the blocks. If we would unconditionally + clear the bitmap here, future changes would be ignored for the page + if it's not in the dirty list (ie, it would be flushed). @return Operation status @retval 0 OK @@ -6494,19 +6502,25 @@ err: uint _ma_apply_redo_free_blocks(MARIA_HA *info, LSN lsn __attribute__((unused)), + LSN redo_lsn, const uchar *header) { MARIA_SHARE *share= info->s; uint ranges; + uint16 sid; DBUG_ENTER("_ma_apply_redo_free_blocks"); share->state.changed|= (STATE_CHANGED | STATE_NOT_ZEROFILLED | STATE_NOT_MOVABLE); + sid= fileid_korr(header); + header+= FILEID_STORE_SIZE; ranges= pagerange_korr(header); header+= PAGERANGE_STORE_SIZE; DBUG_ASSERT(ranges > 0); + /** @todo leave bitmap lock to the bitmap code... */ + pthread_mutex_lock(&share->bitmap.bitmap_lock); while (ranges--) { my_bool res; @@ -6523,18 +6537,22 @@ uint _ma_apply_redo_free_blocks(MARIA_HA *info, DBUG_PRINT("info", ("page: %lu pages: %u", (long) page, page_range)); - /** @todo leave bitmap lock to the bitmap code... */ - pthread_mutex_lock(&share->bitmap.bitmap_lock); - res= _ma_bitmap_reset_full_page_bits(info, &share->bitmap, start_page, - page_range); - pthread_mutex_unlock(&share->bitmap.bitmap_lock); - if (res) + for ( ; page_range-- ; start_page++) { - _ma_mark_file_crashed(share); - DBUG_ASSERT(0); - DBUG_RETURN(res); + if (_ma_redo_not_needed_for_page(sid, redo_lsn, start_page, FALSE)) + continue; + res= _ma_bitmap_reset_full_page_bits(info, &share->bitmap, start_page, + 1); + if (res) + { + pthread_mutex_unlock(&share->bitmap.bitmap_lock); + _ma_mark_file_crashed(share); + DBUG_ASSERT(0); + DBUG_RETURN(res); + } } } + pthread_mutex_unlock(&share->bitmap.bitmap_lock); DBUG_RETURN(0); } @@ -6764,7 +6782,7 @@ uint _ma_apply_redo_insert_row_blobs(MARIA_HA *info, PAGECACHE_LOCK_WRITE_UNLOCK, PAGECACHE_UNPIN, LSN_IMPOSSIBLE, LSN_IMPOSSIBLE, 0, FALSE); - continue; + goto fix_bitmap; } DBUG_ASSERT((found_page_type == (uchar) BLOB_PAGE) || (found_page_type == (uchar) UNALLOCATED_PAGE)); @@ -6799,14 +6817,16 @@ uint _ma_apply_redo_insert_row_blobs(MARIA_HA *info, unlock_method, unpin_method, PAGECACHE_WRITE_DELAY, 0, LSN_IMPOSSIBLE)) goto err; - } + + fix_bitmap: /** @todo leave bitmap lock to the bitmap code... */ - pthread_mutex_lock(&share->bitmap.bitmap_lock); - res= _ma_bitmap_set_full_page_bits(info, &share->bitmap, start_page, - page_range); - pthread_mutex_unlock(&share->bitmap.bitmap_lock); - if (res) - goto err; + pthread_mutex_lock(&share->bitmap.bitmap_lock); + res= _ma_bitmap_set_full_page_bits(info, &share->bitmap, page, + 1); + pthread_mutex_unlock(&share->bitmap.bitmap_lock); + if (res) + goto err; + } } } *first_page= first_page2; diff --git a/storage/maria/ma_blockrec.h b/storage/maria/ma_blockrec.h index a5858880dd0..e63af8eed5b 100644 --- a/storage/maria/ma_blockrec.h +++ b/storage/maria/ma_blockrec.h @@ -235,7 +235,7 @@ uint _ma_apply_redo_insert_row_head_or_tail(MARIA_HA *info, LSN lsn, uint _ma_apply_redo_purge_row_head_or_tail(MARIA_HA *info, LSN lsn, uint page_type, const uchar *header); -uint _ma_apply_redo_free_blocks(MARIA_HA *info, LSN lsn, +uint _ma_apply_redo_free_blocks(MARIA_HA *info, LSN lsn, LSN rec_lsn, const uchar *header); uint _ma_apply_redo_free_head_or_tail(MARIA_HA *info, LSN lsn, const uchar *header); diff --git a/storage/maria/ma_check.c b/storage/maria/ma_check.c index 35dbc7f04d0..5a5e06c5a15 100644 --- a/storage/maria/ma_check.c +++ b/storage/maria/ma_check.c @@ -100,6 +100,9 @@ static my_bool _ma_flush_table_files_before_swap(HA_CHECK *param, static TrID max_trid_in_system(void); static void _ma_check_print_not_visible_error(HA_CHECK *param, TrID used_trid); void retry_if_quick(MARIA_SORT_PARAM *param, int error); +static void print_bitmap_description(MARIA_SHARE *share, + pgcache_page_no_t page, + uchar *buff); /* Initialize check param with default values */ @@ -1842,6 +1845,8 @@ static int check_block_record(HA_CHECK *param, MARIA_HA *info, int extend, } param->used+= block_size; param->link_used+= block_size; + if (param->verbose > 2) + print_bitmap_description(share, page, bitmap_buff); continue; } /* Skip pages marked as empty in bitmap */ @@ -2177,12 +2182,17 @@ int maria_chk_data_link(HA_CHECK *param, MARIA_HA *info, my_bool extend) llstr(param->del_length, llbuff2)); printf("Empty space: %12s Linkdata: %10s\n", llstr(param->empty, llbuff),llstr(param->link_used, llbuff2)); - if (param->lost) - printf("Lost space: %12s", llstr(param->lost, llbuff)); - if (param->max_found_trid) + if (share->data_file_type == BLOCK_RECORD) { - printf("Max trans. id: %11s\n", - llstr(param->max_found_trid, llbuff)); + printf("Full pages: %12s Tail count: %12s\n", + llstr(param->full_page_count, llbuff), + llstr(param->tail_count, llbuff2)); + printf("Lost space: %12s\n", llstr(param->lost, llbuff)); + if (param->max_found_trid) + { + printf("Max trans. id: %11s\n", + llstr(param->max_found_trid, llbuff)); + } } } my_free(record,MYF(0)); @@ -6799,3 +6809,46 @@ void retry_if_quick(MARIA_SORT_PARAM *sort_param, int error) param->testflag|=T_RETRY_WITHOUT_QUICK; } } + +/* Print information about bitmap page */ + +static void print_bitmap_description(MARIA_SHARE *share, + pgcache_page_no_t page, + uchar *bitmap_data) +{ + uchar *pos, *end; + MARIA_FILE_BITMAP *bitmap= &share->bitmap; + uint count=0, dot_printed= 0; + char buff[80], last[80]; + + printf("Bitmap page %lu\n", (ulong) page); + page++; + last[0]=0; + for (pos= bitmap_data, end= pos+ bitmap->used_size ; pos < end ; pos+= 6) + { + ulonglong bits= uint6korr(pos); /* 6 bytes = 6*8/3= 16 patterns */ + uint i; + + for (i= 0; i < 16 ; i++, bits>>= 3) + { + if (count > 60) + { + buff[count]= 0; + if (strcmp(buff, last)) + { + memcpy(last, buff, count+1); + printf("%8lu: %s\n", (ulong) page - count, buff); + dot_printed= 0; + } + else if (!(dot_printed++)) + printf("...\n"); + count= 0; + } + buff[count++]= '0' + (uint) (bits & 7); + page++; + } + } + buff[count]= 0; + printf("%8lu: %s\n", (ulong) page - count, buff); + fputs("\n", stdout); +} diff --git a/storage/maria/ma_recovery.c b/storage/maria/ma_recovery.c index 7a7286e26f9..68384dcec94 100644 --- a/storage/maria/ma_recovery.c +++ b/storage/maria/ma_recovery.c @@ -1643,8 +1643,8 @@ prototype_redo_exec_hook(REDO_FREE_BLOCKS) } buff= log_record_buffer.str; - if (_ma_apply_redo_free_blocks(info, current_group_end_lsn, - buff + FILEID_STORE_SIZE)) + if (_ma_apply_redo_free_blocks(info, current_group_end_lsn, rec->lsn, + buff)) goto end; error= 0; end: @@ -3015,10 +3015,11 @@ static MARIA_HA *get_MARIA_HA_from_REDO_record(const page= page_korr(rec->header + FILEID_STORE_SIZE); llstr(page, llbuf); break; + case LOGREC_REDO_FREE_BLOCKS: /* - For REDO_FREE_BLOCKS, no need to look at dirty pages list: it does not - read data pages, only reads/modifies bitmap page(s) which is cheap. + We are checking against the dirty pages in _ma_apply_redo_free_blocks() */ + break; default: break; } |