Commit 14b99876 authored by marko's avatar marko

branches/zip: Allow dirty blocks to be relocated. Allow a transition

to BUF_BLOCK_ZIP_DIRTY (discarding the uncompressed page corresponding
to a modified compressed page that has not been flushed to disk).

buf_page_can_relocate(): New function, modelled after
buf_flush_ready_for_replace().

buf_LRU_free_block(): Allow the transition to BUF_BLOCK_ZIP_DIRTY.

buf_flush_insert_into_flush_list(): Make the prototype public.

buf_buddy_relocate(): Remove an unnecessary switch statement.
Use buf_page_can_relocate() instead of buf_flush_ready_for_replace().

buf_page_peek(): Made UNIV_INLINE.

Document UNIV_ZIP_DEBUG.
parent 4861c59c
...@@ -400,26 +400,13 @@ buf_buddy_relocate( ...@@ -400,26 +400,13 @@ buf_buddy_relocate(
mutex_enter(mutex); mutex_enter(mutex);
if (buf_flush_ready_for_replace(bpage)) { if (buf_page_can_relocate(bpage)) {
switch (buf_page_get_state(bpage)) { /* Relocate the compressed page. */
case BUF_BLOCK_ZIP_FREE: ut_a(bpage->zip.data == src);
case BUF_BLOCK_NOT_USED: memcpy(dst, src, size);
case BUF_BLOCK_READY_FOR_USE: bpage->zip.data = dst;
case BUF_BLOCK_MEMORY: mutex_exit(mutex);
case BUF_BLOCK_REMOVE_HASH: return(TRUE);
ut_error;
break;
case BUF_BLOCK_ZIP_PAGE:
case BUF_BLOCK_ZIP_DIRTY:
case BUF_BLOCK_FILE_PAGE:
/* Relocate the compressed page. */
ut_a(bpage->zip.data == src);
memcpy(dst, src, size);
bpage->zip.data = dst;
mutex_exit(mutex);
return(TRUE);
}
} }
mutex_exit(mutex); mutex_exit(mutex);
...@@ -444,7 +431,7 @@ buf_buddy_relocate( ...@@ -444,7 +431,7 @@ buf_buddy_relocate(
case BUF_BLOCK_ZIP_PAGE: case BUF_BLOCK_ZIP_PAGE:
mutex_enter(&buf_pool->zip_mutex); mutex_enter(&buf_pool->zip_mutex);
if (buf_flush_ready_for_replace(bpage)) { if (buf_page_can_relocate(bpage)) {
buf_page_t* dpage = (buf_page_t*) dst; buf_page_t* dpage = (buf_page_t*) dst;
buf_page_t* b; buf_page_t* b;
......
...@@ -1387,27 +1387,6 @@ buf_page_peek_if_search_hashed( ...@@ -1387,27 +1387,6 @@ buf_page_peek_if_search_hashed(
return(is_hashed); return(is_hashed);
} }
/************************************************************************
Returns TRUE if the page can be found in the buffer pool hash table. NOTE
that it is possible that the page is not yet read from disk, though. */
ibool
buf_page_peek(
/*==========*/
/* out: TRUE if found from page hash table,
NOTE that the page is not necessarily yet read
from disk! */
ulint space, /* in: space id */
ulint offset) /* in: page number */
{
if (buf_page_peek_block(space, offset)) {
return(TRUE);
}
return(FALSE);
}
#ifdef UNIV_DEBUG_FILE_ACCESSES #ifdef UNIV_DEBUG_FILE_ACCESSES
/************************************************************************ /************************************************************************
Sets file_page_was_freed TRUE if the page is found in the buffer pool. Sets file_page_was_freed TRUE if the page is found in the buffer pool.
......
...@@ -892,11 +892,18 @@ buf_LRU_free_block( ...@@ -892,11 +892,18 @@ buf_LRU_free_block(
ut_ad(buf_page_in_file(bpage)); ut_ad(buf_page_in_file(bpage));
ut_ad(bpage->in_LRU_list); ut_ad(bpage->in_LRU_list);
if (!buf_flush_ready_for_replace(bpage)) { if (!buf_page_can_relocate(bpage)) {
return(FALSE); return(FALSE);
} }
if (bpage->oldest_modification
&& (zip || buf_page_get_state(bpage) == BUF_BLOCK_FILE_PAGE)) {
/* Do not completely free dirty blocks. */
return(FALSE);
}
#ifdef UNIV_DEBUG #ifdef UNIV_DEBUG
if (buf_debug_prints) { if (buf_debug_prints) {
fprintf(stderr, "Putting space %lu page %lu to free list\n", fprintf(stderr, "Putting space %lu page %lu to free list\n",
...@@ -926,7 +933,9 @@ buf_LRU_free_block( ...@@ -926,7 +933,9 @@ buf_LRU_free_block(
ulint fold; ulint fold;
memcpy(b, bpage, sizeof *b); memcpy(b, bpage, sizeof *b);
b->state = BUF_BLOCK_ZIP_PAGE; b->state = b->oldest_modification
? BUF_BLOCK_ZIP_DIRTY
: BUF_BLOCK_ZIP_PAGE;
fold = buf_page_address_fold(b->space, fold = buf_page_address_fold(b->space,
b->offset); b->offset);
...@@ -936,7 +945,11 @@ buf_LRU_free_block( ...@@ -936,7 +945,11 @@ buf_LRU_free_block(
buf_LRU_add_block_low(b, TRUE); buf_LRU_add_block_low(b, TRUE);
buf_LRU_insert_zip_clean(b); if (b->state == BUF_BLOCK_ZIP_PAGE) {
buf_LRU_insert_zip_clean(b);
} else {
buf_flush_insert_into_flush_list(b);
}
mutex_enter(block_mutex); mutex_enter(block_mutex);
......
...@@ -288,7 +288,7 @@ buf_page_make_young( ...@@ -288,7 +288,7 @@ buf_page_make_young(
/************************************************************************ /************************************************************************
Returns TRUE if the page can be found in the buffer pool hash table. NOTE Returns TRUE if the page can be found in the buffer pool hash table. NOTE
that it is possible that the page is not yet read from disk, though. */ that it is possible that the page is not yet read from disk, though. */
UNIV_INLINE
ibool ibool
buf_page_peek( buf_page_peek(
/*==========*/ /*==========*/
...@@ -702,6 +702,16 @@ buf_block_set_io_fix( ...@@ -702,6 +702,16 @@ buf_block_set_io_fix(
buf_block_t* block, /* in/out: control block */ buf_block_t* block, /* in/out: control block */
enum buf_io_fix io_fix);/* in: io_fix state */ enum buf_io_fix io_fix);/* in: io_fix state */
/************************************************************************
Determine if a buffer block can be relocated in memory. The block
can be dirty, but it must not be I/O-fixed or bufferfixed. */
UNIV_INLINE
ibool
buf_page_can_relocate(
/*==================*/
const buf_page_t* bpage) /* control block being relocated */
__attribute__((const));
/************************************************************************* /*************************************************************************
Determine if a block has been flagged old. */ Determine if a block has been flagged old. */
UNIV_INLINE UNIV_INLINE
......
...@@ -11,6 +11,22 @@ Created 11/5/1995 Heikki Tuuri ...@@ -11,6 +11,22 @@ Created 11/5/1995 Heikki Tuuri
#include "buf0rea.h" #include "buf0rea.h"
#include "mtr0mtr.h" #include "mtr0mtr.h"
/************************************************************************
Returns TRUE if the page can be found in the buffer pool hash table. NOTE
that it is possible that the page is not yet read from disk, though. */
UNIV_INLINE
ibool
buf_page_peek(
/*==========*/
/* out: TRUE if found from page hash table,
NOTE that the page is not necessarily yet read
from disk! */
ulint space, /* in: space id */
ulint offset) /* in: page number */
{
return(buf_page_peek_block(space, offset) != NULL);
}
/************************************************************************ /************************************************************************
Reads the freed_page_clock of a buffer block. */ Reads the freed_page_clock of a buffer block. */
UNIV_INLINE UNIV_INLINE
...@@ -386,6 +402,26 @@ buf_block_set_io_fix( ...@@ -386,6 +402,26 @@ buf_block_set_io_fix(
buf_page_set_io_fix(&block->page, io_fix); buf_page_set_io_fix(&block->page, io_fix);
} }
/************************************************************************
Determine if a buffer block can be relocated in memory. The block
can be dirty, but it must not be I/O-fixed or bufferfixed. */
UNIV_INLINE
ibool
buf_page_can_relocate(
/*==================*/
const buf_page_t* bpage) /* control block being relocated */
{
#ifdef UNIV_SYNC_DEBUG
ut_a(mutex_own(&buf_pool->mutex));
ut_a(mutex_own(buf_page_get_mutex((buf_page_t*) bpage)));
#endif /* UNIV_SYNC_DEBUG */
ut_ad(buf_page_in_file(bpage));
ut_ad(bpage->in_LRU_list);
return(buf_page_get_io_fix(bpage) == BUF_IO_NONE
&& bpage->buf_fix_count == 0);
}
/************************************************************************* /*************************************************************************
Determine if a block has been flagged old. */ Determine if a block has been flagged old. */
UNIV_INLINE UNIV_INLINE
......
...@@ -14,6 +14,13 @@ Created 11/5/1995 Heikki Tuuri ...@@ -14,6 +14,13 @@ Created 11/5/1995 Heikki Tuuri
#include "ut0byte.h" #include "ut0byte.h"
#include "mtr0types.h" #include "mtr0types.h"
/************************************************************************
Inserts a modified block into the flush list. */
void
buf_flush_insert_into_flush_list(
/*=============================*/
buf_page_t* bpage); /* in: block which is modified */
/************************************************************************ /************************************************************************
Remove a block from the flush list of modified blocks. */ Remove a block from the flush list of modified blocks. */
...@@ -102,6 +109,7 @@ buf_flush_recv_note_modification( ...@@ -102,6 +109,7 @@ buf_flush_recv_note_modification(
/************************************************************************ /************************************************************************
Returns TRUE if the file page block is immediately suitable for replacement, Returns TRUE if the file page block is immediately suitable for replacement,
i.e., transition FILE_PAGE => NOT_USED allowed. */ i.e., transition FILE_PAGE => NOT_USED allowed. */
ibool ibool
buf_flush_ready_for_replace( buf_flush_ready_for_replace(
/*========================*/ /*========================*/
......
...@@ -9,13 +9,6 @@ Created 11/5/1995 Heikki Tuuri ...@@ -9,13 +9,6 @@ Created 11/5/1995 Heikki Tuuri
#include "buf0buf.h" #include "buf0buf.h"
#include "mtr0mtr.h" #include "mtr0mtr.h"
/************************************************************************
Inserts a modified block into the flush list. */
void
buf_flush_insert_into_flush_list(
/*=============================*/
buf_page_t* bpage); /* in: block which is modified */
/************************************************************************ /************************************************************************
Inserts a modified block into the flush list in the right sorted position. Inserts a modified block into the flush list in the right sorted position.
This function is used by recovery, because there the modifications do not This function is used by recovery, because there the modifications do not
......
...@@ -103,7 +103,8 @@ operations (very slow); also UNIV_DEBUG must be defined */ ...@@ -103,7 +103,8 @@ operations (very slow); also UNIV_DEBUG must be defined */
in sync0sync.c */ in sync0sync.c */
#define UNIV_BTR_PRINT /* enable functions for #define UNIV_BTR_PRINT /* enable functions for
printing B-trees */ printing B-trees */
#define UNIV_ZIP_DEBUG #define UNIV_ZIP_DEBUG /* extensive consistency checks
for compressed pages */
#endif #endif
#define UNIV_BTR_DEBUG /* check B-tree links */ #define UNIV_BTR_DEBUG /* check B-tree links */
......
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