1 # name : innodb_opt_lru_count.patch
2 # introduced : 11 or before
3 # maintainer : Yasufumi
6 # Any small change to this file in the main branch
7 # should be done or reviewed by the maintainer!
8 --- a/storage/innobase/buf/buf0buddy.c
9 +++ b/storage/innobase/buf/buf0buddy.c
12 ut_d(BUF_BUDDY_LIST_VALIDATE(buf_pool, i));
14 - bpage = UT_LIST_GET_FIRST(buf_pool->zip_free[i]);
15 + bpage = UT_LIST_GET_LAST(buf_pool->zip_free[i]);
18 ut_a(buf_page_get_state(bpage) == BUF_BLOCK_ZIP_FREE);
19 --- a/storage/innobase/buf/buf0buf.c
20 +++ b/storage/innobase/buf/buf0buf.c
22 block->page.in_zip_hash = FALSE;
23 block->page.in_flush_list = FALSE;
24 block->page.in_free_list = FALSE;
25 - block->page.in_LRU_list = FALSE;
26 block->in_unzip_LRU_list = FALSE;
27 #endif /* UNIV_DEBUG */
28 + block->page.in_LRU_list = FALSE;
29 #if defined UNIV_AHI_DEBUG || defined UNIV_DEBUG
30 block->n_pointers = 0;
31 #endif /* UNIV_AHI_DEBUG || UNIV_DEBUG */
34 memcpy(dpage, bpage, sizeof *dpage);
36 - ut_d(bpage->in_LRU_list = FALSE);
37 + bpage->in_LRU_list = FALSE;
38 ut_d(bpage->in_page_hash = FALSE);
40 /* relocate buf_pool->LRU */
42 bpage->in_zip_hash = FALSE;
43 bpage->in_flush_list = FALSE;
44 bpage->in_free_list = FALSE;
45 - bpage->in_LRU_list = FALSE;
46 #endif /* UNIV_DEBUG */
47 + bpage->in_LRU_list = FALSE;
49 ut_d(bpage->in_page_hash = TRUE);
52 ibuf_merge_or_delete_for_page(NULL, space, offset, zip_size, TRUE);
54 /* Flush pages from the end of the LRU list if necessary */
55 - buf_flush_free_margin(buf_pool);
56 + buf_flush_free_margin(buf_pool, FALSE);
60 --- a/storage/innobase/buf/buf0flu.c
61 +++ b/storage/innobase/buf/buf0flu.c
63 buf_page_in_file(bpage) and in the LRU list */
66 - buf_pool_t* buf_pool = buf_pool_from_bpage(bpage);
67 - ut_ad(buf_pool_mutex_own(buf_pool));
68 + //buf_pool_t* buf_pool = buf_pool_from_bpage(bpage);
69 + //ut_ad(buf_pool_mutex_own(buf_pool));
71 - ut_ad(mutex_own(buf_page_get_mutex(bpage)));
72 - ut_ad(bpage->in_LRU_list);
73 + //ut_ad(mutex_own(buf_page_get_mutex(bpage)));
74 + //ut_ad(bpage->in_LRU_list);
76 - if (UNIV_LIKELY(buf_page_in_file(bpage))) {
77 + if (UNIV_LIKELY(bpage->in_LRU_list && buf_page_in_file(bpage))) {
79 return(bpage->oldest_modification == 0
80 && buf_page_get_io_fix(bpage) == BUF_IO_NONE
81 && bpage->buf_fix_count == 0);
84 + /* permited not to own LRU_mutex.. */
86 ut_print_timestamp(stderr);
88 " InnoDB: Error: buffer block state %lu"
90 (ulong) buf_page_get_state(bpage));
91 ut_print_buf(stderr, bpage, sizeof(buf_page_t));
97 @@ -2049,8 +2052,14 @@
101 + ibool have_LRU_mutex = FALSE;
103 - buf_pool_mutex_enter(buf_pool);
104 + if(UT_LIST_GET_LEN(buf_pool->unzip_LRU))
105 + have_LRU_mutex = TRUE;
107 + //buf_pool_mutex_enter(buf_pool);
108 + if (have_LRU_mutex)
109 + buf_pool_mutex_enter(buf_pool);
111 n_replaceable = UT_LIST_GET_LEN(buf_pool->free);
113 @@ -2061,7 +2070,13 @@
114 + BUF_FLUSH_EXTRA_MARGIN(buf_pool))
115 && (distance < BUF_LRU_FREE_SEARCH_LEN(buf_pool))) {
117 - mutex_t* block_mutex = buf_page_get_mutex(bpage);
118 + mutex_t* block_mutex;
119 + if (!bpage->in_LRU_list) {
120 + /* reatart. but it is very optimistic */
121 + bpage = UT_LIST_GET_LAST(buf_pool->LRU);
124 + block_mutex = buf_page_get_mutex(bpage);
126 mutex_enter(block_mutex);
128 @@ -2076,11 +2091,18 @@
129 bpage = UT_LIST_GET_PREV(LRU, bpage);
132 - buf_pool_mutex_exit(buf_pool);
133 + //buf_pool_mutex_exit(buf_pool);
134 + if (have_LRU_mutex)
135 + buf_pool_mutex_exit(buf_pool);
137 if (n_replaceable >= BUF_FLUSH_FREE_BLOCK_MARGIN(buf_pool)) {
140 + } else if (!have_LRU_mutex) {
141 + /* confirm it again with LRU_mutex for exactness */
142 + have_LRU_mutex = TRUE;
147 return(BUF_FLUSH_FREE_BLOCK_MARGIN(buf_pool)
148 @@ -2098,7 +2120,8 @@
150 buf_flush_free_margin(
151 /*==================*/
152 - buf_pool_t* buf_pool) /*!< in: Buffer pool instance */
153 + buf_pool_t* buf_pool, /*!< in: Buffer pool instance */
158 @@ -2109,7 +2132,7 @@
160 n_flushed = buf_flush_LRU(buf_pool, n_to_flush);
162 - if (n_flushed == ULINT_UNDEFINED) {
163 + if (wait && n_flushed == ULINT_UNDEFINED) {
164 /* There was an LRU type flush batch already running;
165 let us wait for it to end */
167 @@ -2122,8 +2145,9 @@
168 Flushes pages from the end of all the LRU lists. */
171 -buf_flush_free_margins(void)
172 +buf_flush_free_margins(
173 /*========================*/
178 @@ -2132,7 +2156,7 @@
180 buf_pool = buf_pool_from_array(i);
182 - buf_flush_free_margin(buf_pool);
183 + buf_flush_free_margin(buf_pool, wait);
187 --- a/storage/innobase/buf/buf0lru.c
188 +++ b/storage/innobase/buf/buf0lru.c
191 /* No free block was found: try to flush the LRU list */
193 - buf_flush_free_margin(buf_pool);
194 + buf_flush_free_margin(buf_pool, TRUE);
195 ++srv_buf_pool_wait_free;
197 os_aio_simulated_wake_handler_threads();
198 @@ -1131,7 +1131,7 @@
200 /* Remove the block from the LRU list */
201 UT_LIST_REMOVE(LRU, buf_pool->LRU, bpage);
202 - ut_d(bpage->in_LRU_list = FALSE);
203 + bpage->in_LRU_list = FALSE;
205 buf_unzip_LRU_remove_block_if_needed(bpage);
207 @@ -1210,7 +1210,7 @@
209 ut_ad(!bpage->in_LRU_list);
210 UT_LIST_ADD_LAST(LRU, buf_pool->LRU, bpage);
211 - ut_d(bpage->in_LRU_list = TRUE);
212 + bpage->in_LRU_list = TRUE;
214 if (UT_LIST_GET_LEN(buf_pool->LRU) > BUF_LRU_OLD_MIN_LEN) {
216 @@ -1280,7 +1280,7 @@
217 buf_pool->LRU_old_len++;
220 - ut_d(bpage->in_LRU_list = TRUE);
221 + bpage->in_LRU_list = TRUE;
223 if (UT_LIST_GET_LEN(buf_pool->LRU) > BUF_LRU_OLD_MIN_LEN) {
225 @@ -1524,7 +1524,7 @@
226 buf_page_set_old(b, buf_page_is_old(b));
227 #endif /* UNIV_LRU_DEBUG */
229 - ut_d(b->in_LRU_list = FALSE);
230 + b->in_LRU_list = FALSE;
231 buf_LRU_add_block_low(b, buf_page_is_old(b));
234 --- a/storage/innobase/buf/buf0rea.c
235 +++ b/storage/innobase/buf/buf0rea.c
239 /* Flush pages from the end of the LRU list if necessary */
240 - buf_flush_free_margin(buf_pool);
241 + buf_flush_free_margin(buf_pool, TRUE);
243 /* Increment number of I/O operations used for LRU policy. */
244 buf_LRU_stat_inc_io();
246 os_aio_simulated_wake_handler_threads();
248 /* Flush pages from the end of the LRU list if necessary */
249 - buf_flush_free_margin(buf_pool);
250 + buf_flush_free_margin(buf_pool, TRUE);
253 if (buf_debug_prints && (count > 0)) {
255 os_aio_simulated_wake_handler_threads();
257 /* Flush pages from the end of all the LRU lists if necessary */
258 - buf_flush_free_margins();
259 + buf_flush_free_margins(FALSE);
262 if (buf_debug_prints) {
264 os_aio_simulated_wake_handler_threads();
266 /* Flush pages from the end of all the LRU lists if necessary */
267 - buf_flush_free_margins();
268 + buf_flush_free_margins(FALSE);
271 if (buf_debug_prints) {
272 --- a/storage/innobase/include/buf0buf.h
273 +++ b/storage/innobase/include/buf0buf.h
274 @@ -1424,11 +1424,11 @@
276 UT_LIST_NODE_T(buf_page_t) LRU;
277 /*!< node of the LRU list */
280 ibool in_LRU_list; /*!< TRUE if the page is in
281 the LRU list; used in
283 -#endif /* UNIV_DEBUG */
284 +//#endif /* UNIV_DEBUG */
285 unsigned old:1; /*!< TRUE if the block is in the old
286 blocks in buf_pool->LRU_old */
287 unsigned freed_page_clock:31;/*!< the value of
288 --- a/storage/innobase/include/buf0flu.h
289 +++ b/storage/innobase/include/buf0flu.h
292 buf_flush_free_margin(
293 /*==================*/
294 - buf_pool_t* buf_pool);
295 + buf_pool_t* buf_pool,
297 /*********************************************************************//**
298 Flushes pages from the end of all the LRU lists. */
301 -buf_flush_free_margins(void);
302 +buf_flush_free_margins(
303 /*=========================*/
305 #endif /* !UNIV_HOTBACKUP */
306 /********************************************************************//**
307 Initializes a page for writing to the tablespace. */