diff options
author | unknown <bell@pwbook.sanja.is.com.ua> | 2007-04-04 23:37:09 +0300 |
---|---|---|
committer | unknown <bell@pwbook.sanja.is.com.ua> | 2007-04-04 23:37:09 +0300 |
commit | 39d64a1d2565b09307d11b2a665f3f2c6bc8106e (patch) | |
tree | f06eaccb6a5b46b3894e7939c81911d30e765fd5 | |
parent | a3f9083bb4649530b210423e21589803c075bb9e (diff) | |
download | mariadb-git-39d64a1d2565b09307d11b2a665f3f2c6bc8106e.tar.gz |
Pagecache integration for review.
storage/maria/unittest/ma_pagecache_single.c:
Rename: storage/maria/unittest/mf_pagecache_single.c -> storage/maria/unittest/ma_pagecache_single.c
include/maria.h:
Pagecache integration.
include/myisamchk.h:
Pagecache integration.
include/pagecache.h:
removed WRITE_NOW mode
Pagecache parameters management.
mysys/Makefile.am:
Safe hash procedures moved to the separate file.
Pagecache moved to maria engine directory.
mysys/mf_keycaches.c:
Safe hash procedures moved to the separate file.
sql/handler.cc:
Pageccahe integration.
sql/handler.h:
Pagecache integration.
sql/mysql_priv.h:
pagecache integration
sql/mysqld.cc:
pagecache integration
sql/set_var.cc:
Pagecache integration.
sql/set_var.h:
Pagecache integration.
storage/maria/Makefile.am:
Pagecache integration and moving to maria engine directory.
storage/maria/ha_maria.cc:
File changed on PAGECCAHE_FILE.
storage/maria/ma_bitmap.c:
Pagecache integration.
storage/maria/ma_blockrec.c:
Pagecache integration.
storage/maria/ma_check.c:
File changed on PAGECCAHE_FILE.
Pagecache integration.
storage/maria/ma_close.c:
File changed on PAGECCAHE_FILE.
storage/maria/ma_delete_all.c:
File changed on PAGECCAHE_FILE.
storage/maria/ma_dynrec.c:
File changed on PAGECCAHE_FILE.
storage/maria/ma_extra.c:
File changed on PAGECCAHE_FILE.
storage/maria/ma_info.c:
File changed on PAGECCAHE_FILE.
storage/maria/ma_keycache.c:
Pagecache integration.
storage/maria/ma_locking.c:
File changed on PAGECCAHE_FILE.
storage/maria/ma_loghandler.c:
Assert added.
storage/maria/ma_loghandler.h:
extern specifier added.
storage/maria/ma_open.c:
Pagecache integration.
File changed on PAGECCAHE_FILE.
storage/maria/ma_packrec.c:
File changed on PAGECCAHE_FILE.
storage/maria/ma_page.c:
Pagecache integration.
storage/maria/ma_pagecache.c:
Pagecache renamed and moved to the maria directory.
BLOCK_* defines renamed to avoid conflict with BLOCK_ERROR defined in maria_def.h
storage/maria/ma_panic.c:
File changed on PAGECCAHE_FILE.
storage/maria/ma_preload.c:
Pagecache integration.
File changed on PAGECCAHE_FILE.
storage/maria/ma_static.c:
Pagecache integration.
storage/maria/ma_test1.c:
Pagecache integration.
storage/maria/ma_test2.c:
Pagecache integration.
storage/maria/ma_test3.c:
Pagecache integration.
storage/maria/ma_write.c:
File changed on PAGECCAHE_FILE.
storage/maria/maria_chk.c:
Pagecache integration.
File changed on PAGECCAHE_FILE.
storage/maria/maria_def.h:
Pagecache integration.
File changed on PAGECCAHE_FILE.
storage/maria/maria_ftdump.c:
Pagecache integration.
storage/maria/maria_pack.c:
File changed on PAGECCAHE_FILE.
storage/maria/unittest/Makefile.am:
Pagecache moved to the maria directory.
storage/maria/unittest/ma_pagecache_consist.c:
fixed using uninitialized variable
storage/maria/ma_pagecaches.c:
New BitKeeper file ``storage/maria/ma_pagecaches.c''
mysys/my_safehash.h:
New BitKeeper file ``mysys/my_safehash.h''
45 files changed, 1291 insertions, 885 deletions
diff --git a/include/maria.h b/include/maria.h index 94152ce9bfa..6777d8b1b63 100644 --- a/include/maria.h +++ b/include/maria.h @@ -27,8 +27,8 @@ extern "C" { #ifndef _m_ctype_h #include <m_ctype.h> #endif -#ifndef _keycache_h -#include "keycache.h" +#ifndef _pagecache_h +#include "pagecache.h" #endif #include "my_handler.h" #include "ft_global.h" @@ -248,7 +248,7 @@ extern my_bool maria_flush, maria_single_user; extern my_bool maria_delay_key_write, maria_delay_rec_write; extern my_off_t maria_max_temp_length; extern ulong maria_bulk_insert_tree_size, maria_data_pointer_size; -extern KEY_CACHE maria_key_cache_var, *maria_key_cache; +extern PAGECACHE maria_pagecache_var, *maria_pagecache; /* Prototypes for maria-functions */ @@ -417,10 +417,10 @@ my_bool maria_test_if_sort_rep(MARIA_HA *info, ha_rows rows, ulonglong key_map, int maria_init_bulk_insert(MARIA_HA *info, ulong cache_size, ha_rows rows); void maria_flush_bulk_insert(MARIA_HA *info, uint inx); void maria_end_bulk_insert(MARIA_HA *info); -int maria_assign_to_key_cache(MARIA_HA *info, ulonglong key_map, - KEY_CACHE *key_cache); -void maria_change_key_cache(KEY_CACHE *old_key_cache, - KEY_CACHE *new_key_cache); +int maria_assign_to_pagecache(MARIA_HA *info, ulonglong key_map, + PAGECACHE *key_cache); +void maria_change_pagecache(PAGECACHE *old_key_cache, + PAGECACHE *new_key_cache); int maria_preload(MARIA_HA *info, ulonglong key_map, my_bool ignore_leaves); /* fulltext functions */ diff --git a/include/myisamchk.h b/include/myisamchk.h index 66d0a77b62f..887cf835b87 100644 --- a/include/myisamchk.h +++ b/include/myisamchk.h @@ -133,7 +133,7 @@ typedef struct st_handler_check_param ulong rec_per_key_part[HA_MAX_KEY_SEG * HA_MAX_POSSIBLE_KEY]; uint out_flag, warning_printed, error_printed, verbose; uint opt_sort_key, total_files, max_level; - uint testflag, key_cache_block_size; + uint testflag, key_cache_block_size, pagecache_block_size; int tmpfile_createflag, err_count; myf myf_rw; uint8 language; diff --git a/include/pagecache.h b/include/pagecache.h index 32e23fb54ea..08ecc7e5f4a 100644 --- a/include/pagecache.h +++ b/include/pagecache.h @@ -66,8 +66,6 @@ enum pagecache_write_mode { /* do not write immediately, i.e. it will be dirty page */ PAGECACHE_WRITE_DELAY, - /* write page to the file and put it to the cache */ - PAGECACHE_WRITE_NOW, /* page already is in the file. (key cache insert analogue) */ PAGECACHE_WRITE_DONE }; @@ -162,6 +160,9 @@ typedef struct st_pagecache my_bool in_init; /* Set to 1 in MySQL during init/resize */ } PAGECACHE; +/* The default key cache */ +extern PAGECACHE dflt_pagecache_var, *dflt_pagecache; + extern int init_pagecache(PAGECACHE *pagecache, my_size_t use_mem, uint division_limit, uint age_threshold, uint block_size); @@ -184,16 +185,22 @@ extern byte *pagecache_valid_read(PAGECACHE *pagecache, PAGECACHE_PAGE_LINK *link, pagecache_disk_read_validator validator, gptr validator_data); -extern my_bool pagecache_write(PAGECACHE *pagecache, - PAGECACHE_FILE *file, - pgcache_page_no_t pageno, - uint level, - byte *buff, - enum pagecache_page_type type, - enum pagecache_page_lock lock, - enum pagecache_page_pin pin, - enum pagecache_write_mode write_mode, - PAGECACHE_PAGE_LINK *link); + +#define pagecache_write(P,F,N,L,B,T,O,I,M,K) \ + pagecache_write_part(P,F,N,L,B,T,O,I,M,K,0,(P)->block_size) + +extern my_bool pagecache_write_part(PAGECACHE *pagecache, + PAGECACHE_FILE *file, + pgcache_page_no_t pageno, + uint level, + byte *buff, + enum pagecache_page_type type, + enum pagecache_page_lock lock, + enum pagecache_page_pin pin, + enum pagecache_write_mode write_mode, + PAGECACHE_PAGE_LINK *link, + uint offset, + uint size); extern void pagecache_unlock_page(PAGECACHE *pagecache, PAGECACHE_FILE *file, pgcache_page_no_t pageno, @@ -224,5 +231,18 @@ extern my_bool pagecache_collect_changed_blocks_with_lsn(PAGECACHE *pagecache, LSN *max_lsn); extern int reset_pagecache_counters(const char *name, PAGECACHE *pagecache); + +/* Functions to handle multiple key caches */ +extern my_bool multi_pagecache_init(void); +extern void multi_pagecache_free(void); +extern PAGECACHE *multi_pagecache_search(byte *key, uint length, + PAGECACHE *def); +extern my_bool multi_pagecache_set(const byte *key, uint length, + PAGECACHE *pagecache); +extern void multi_pagecache_change(PAGECACHE *old_data, + PAGECACHE *new_data); +extern int reset_pagecache_counters(const char *name, + PAGECACHE *pagecache); + C_MODE_END #endif /* _keycache_h */ diff --git a/mysys/Makefile.am b/mysys/Makefile.am index bec72263ba4..3c686733b59 100644 --- a/mysys/Makefile.am +++ b/mysys/Makefile.am @@ -26,6 +26,7 @@ libmysys_a_SOURCES = my_init.c my_getwd.c mf_getdate.c my_mmap.c \ mf_path.c mf_loadpath.c my_file.c \ my_open.c my_create.c my_dup.c my_seek.c my_read.c \ my_pread.c my_write.c my_getpagesize.c \ + my_safehash.c \ mf_keycache.c mf_keycaches.c my_crc32.c \ mf_iocache.c mf_iocache2.c mf_cache.c mf_tempfile.c \ mf_tempdir.c my_lock.c mf_brkhant.c my_alarm.c \ @@ -55,7 +56,7 @@ libmysys_a_SOURCES = my_init.c my_getwd.c mf_getdate.c my_mmap.c \ my_handler.c my_netware.c my_largepage.c \ my_memmem.c \ my_windac.c my_access.c base64.c my_libwrap.c \ - mf_pagecache.c wqueue.c + wqueue.c EXTRA_DIST = thr_alarm.c thr_lock.c my_pthread.c my_thr_init.c \ thr_mutex.c thr_rwlock.c \ CMakeLists.txt mf_soundex.c \ diff --git a/mysys/mf_keycaches.c b/mysys/mf_keycaches.c index 4c20f69053d..39ff536d3e0 100644 --- a/mysys/mf_keycaches.c +++ b/mysys/mf_keycaches.c @@ -1,4 +1,4 @@ -/* Copyright (C) 2003 MySQL AB +/* Copyright (C) 2003-2007 MySQL AB 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 @@ -26,270 +26,7 @@ #include <keycache.h> #include <hash.h> #include <m_string.h> - -/***************************************************************************** - General functions to handle SAFE_HASH objects. - - A SAFE_HASH object is used to store the hash, the mutex and default value - needed by the rest of the key cache code. - This is a separate struct to make it easy to later reuse the code for other - purposes - - All entries are linked in a list to allow us to traverse all elements - and delete selected ones. (HASH doesn't allow any easy ways to do this). -*****************************************************************************/ - -/* - Struct to store a key and pointer to object -*/ - -typedef struct st_safe_hash_entry -{ - byte *key; - uint length; - byte *data; - struct st_safe_hash_entry *next, **prev; -} SAFE_HASH_ENTRY; - - -typedef struct st_safe_hash_with_default -{ -#ifdef THREAD - rw_lock_t mutex; -#endif - HASH hash; - byte *default_value; - SAFE_HASH_ENTRY *root; -} SAFE_HASH; - - -/* - Free a SAFE_HASH_ENTRY - - This function is called by the hash object on delete -*/ - -static void safe_hash_entry_free(SAFE_HASH_ENTRY *entry) -{ - DBUG_ENTER("free_assign_entry"); - my_free((gptr) entry, MYF(0)); - DBUG_VOID_RETURN; -} - - -/* Get key and length for a SAFE_HASH_ENTRY */ - -static byte *safe_hash_entry_get(SAFE_HASH_ENTRY *entry, uint *length, - my_bool not_used __attribute__((unused))) -{ - *length=entry->length; - return (byte*) entry->key; -} - - -/* - Init a SAFE_HASH object - - SYNOPSIS - safe_hash_init() - hash safe_hash handler - elements Expected max number of elements - default_value default value - - NOTES - In case of error we set hash->default_value to 0 to allow one to call - safe_hash_free on an object that couldn't be initialized. - - RETURN - 0 ok - 1 error -*/ - -static my_bool safe_hash_init(SAFE_HASH *hash, uint elements, - byte *default_value) -{ - DBUG_ENTER("safe_hash"); - if (hash_init(&hash->hash, &my_charset_bin, elements, - 0, 0, (hash_get_key) safe_hash_entry_get, - (void (*)(void*)) safe_hash_entry_free, 0)) - { - hash->default_value= 0; - DBUG_RETURN(1); - } - my_rwlock_init(&hash->mutex, 0); - hash->default_value= default_value; - hash->root= 0; - DBUG_RETURN(0); -} - - -/* - Free a SAFE_HASH object - - NOTES - This is safe to call on any object that has been sent to safe_hash_init() -*/ - -static void safe_hash_free(SAFE_HASH *hash) -{ - /* - Test if safe_hash_init succeeded. This will also guard us against multiple - free calls. - */ - if (hash->default_value) - { - hash_free(&hash->hash); - rwlock_destroy(&hash->mutex); - hash->default_value=0; - } -} - -/* - Return the value stored for a key or default value if no key -*/ - -static byte *safe_hash_search(SAFE_HASH *hash, const byte *key, uint length, - byte *def) -{ - byte *result; - DBUG_ENTER("safe_hash_search"); - rw_rdlock(&hash->mutex); - result= hash_search(&hash->hash, key, length); - rw_unlock(&hash->mutex); - if (!result) - result= def; - else - result= ((SAFE_HASH_ENTRY*) result)->data; - DBUG_PRINT("exit",("data: 0x%lx", (long) result)); - DBUG_RETURN(result); -} - - -/* - Associate a key with some data - - SYONOPSIS - safe_hash_set() - hash Hash handle - key key (path to table etc..) - length Length of key - data data to to associate with the data - - NOTES - This can be used both to insert a new entry and change an existing - entry. - If one associates a key with the default key cache, the key is deleted - - RETURN - 0 ok - 1 error (Can only be EOM). In this case my_message() is called. -*/ - -static my_bool safe_hash_set(SAFE_HASH *hash, const byte *key, uint length, - byte *data) -{ - SAFE_HASH_ENTRY *entry; - my_bool error= 0; - DBUG_ENTER("safe_hash_set"); - DBUG_PRINT("enter",("key: %.*s data: 0x%lx", length, key, (long) data)); - - rw_wrlock(&hash->mutex); - entry= (SAFE_HASH_ENTRY*) hash_search(&hash->hash, key, length); - - if (data == hash->default_value) - { - /* - The key is to be associated with the default entry. In this case - we can just delete the entry (if it existed) from the hash as a - search will return the default entry - */ - if (!entry) /* nothing to do */ - goto end; - /* unlink entry from list */ - if ((*entry->prev= entry->next)) - entry->next->prev= entry->prev; - hash_delete(&hash->hash, (byte*) entry); - goto end; - } - if (entry) - { - /* Entry existed; Just change the pointer to point at the new data */ - entry->data= data; - } - else - { - if (!(entry= (SAFE_HASH_ENTRY *) my_malloc(sizeof(*entry) + length, - MYF(MY_WME)))) - { - error= 1; - goto end; - } - entry->key= (byte*) (entry +1); - memcpy((char*) entry->key, (char*) key, length); - entry->length= length; - entry->data= data; - /* Link entry to list */ - if ((entry->next= hash->root)) - entry->next->prev= &entry->next; - entry->prev= &hash->root; - hash->root= entry; - if (my_hash_insert(&hash->hash, (byte*) entry)) - { - /* This can only happen if hash got out of memory */ - my_free((char*) entry, MYF(0)); - error= 1; - goto end; - } - } - -end: - rw_unlock(&hash->mutex); - DBUG_RETURN(error); -} - - -/* - Change all entres with one data value to another data value - - SYONOPSIS - safe_hash_change() - hash Hash handle - old_data Old data - new_data Change all 'old_data' to this - - NOTES - We use the linked list to traverse all elements in the hash as - this allows us to delete elements in the case where 'new_data' is the - default value. -*/ - -static void safe_hash_change(SAFE_HASH *hash, byte *old_data, byte *new_data) -{ - SAFE_HASH_ENTRY *entry, *next; - DBUG_ENTER("safe_hash_set"); - - rw_wrlock(&hash->mutex); - - for (entry= hash->root ; entry ; entry= next) - { - next= entry->next; - if (entry->data == old_data) - { - if (new_data == hash->default_value) - { - if ((*entry->prev= entry->next)) - entry->next->prev= entry->prev; - hash_delete(&hash->hash, (byte*) entry); - } - else - entry->data= new_data; - } - } - - rw_unlock(&hash->mutex); - DBUG_VOID_RETURN; -} - +#include "my_safehash.h" /***************************************************************************** Functions to handle the key cache objects @@ -366,3 +103,5 @@ void multi_key_cache_change(KEY_CACHE *old_data, { safe_hash_change(&key_cache_hash, (byte*) old_data, (byte*) new_data); } + + diff --git a/mysys/my_safehash.h b/mysys/my_safehash.h new file mode 100644 index 00000000000..53845a5fec7 --- /dev/null +++ b/mysys/my_safehash.h @@ -0,0 +1,58 @@ +/* Copyright (C) 2003 MySQL AB + + 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; either version 2 of the License, or + (at your option) any later version. + + 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 */ + +/* + Handling of multiple key caches + + The idea is to have a thread safe hash on the table name, + with a default key cache value that is returned if the table name is not in + the cache. +*/ + +#include <hash.h> + +/* + Struct to store a key and pointer to object +*/ + +typedef struct st_safe_hash_entry +{ + byte *key; + uint length; + byte *data; + struct st_safe_hash_entry *next, **prev; +} SAFE_HASH_ENTRY; + + +typedef struct st_safe_hash_with_default +{ +#ifdef THREAD + rw_lock_t mutex; +#endif + HASH hash; + byte *default_value; + SAFE_HASH_ENTRY *root; +} SAFE_HASH; + + +my_bool safe_hash_init(SAFE_HASH *hash, uint elements, + byte *default_value); +void safe_hash_free(SAFE_HASH *hash); +byte *safe_hash_search(SAFE_HASH *hash, const byte *key, uint length, + byte *def); +my_bool safe_hash_set(SAFE_HASH *hash, const byte *key, uint length, + byte *data); +void safe_hash_change(SAFE_HASH *hash, byte *old_data, byte *new_data); diff --git a/sql/handler.cc b/sql/handler.cc index ce9dc342713..fe31f912381 100644 --- a/sql/handler.cc +++ b/sql/handler.cc @@ -28,6 +28,10 @@ #include <myisampack.h> #include <errno.h> +#ifdef WITH_MARIA_STORAGE_ENGINE +#include <maria.h> +#endif + #ifdef WITH_PARTITION_STORAGE_ENGINE #include "ha_partition.h" #endif @@ -2773,6 +2777,99 @@ int ha_change_key_cache(KEY_CACHE *old_key_cache, } +/***************************************************************************** + pagecache handling. + + This code is only relevant for maria tables + + pagecache->cache may be 0 only in the case where a key cache is not + initialized or when we where not able to init the key cache in a previous + call to ha_init_pagecache() (probably out of memory) +*****************************************************************************/ + + +#ifdef WITH_MARIA_STORAGE_ENGINE + +/* Init a pagecache if it has not been initied before */ + +int ha_init_pagecache(const char *name, PAGECACHE *pagecache) +{ + DBUG_ENTER("ha_init_key_cache"); + + if (!pagecache->inited) + { + pthread_mutex_lock(&LOCK_global_system_variables); + long tmp_buff_size= (long) pagecache->param_buff_size; + long tmp_block_size= (long) pagecache->param_block_size; + uint division_limit= pagecache->param_division_limit; + uint age_threshold= pagecache->param_age_threshold; + pthread_mutex_unlock(&LOCK_global_system_variables); + DBUG_RETURN(!init_pagecache(pagecache, + tmp_buff_size, division_limit, age_threshold, + tmp_block_size)); + } + DBUG_RETURN(0); +} + + +/* Resize key cache */ +/* +TODO: uncomment when resize will be implemented +int ha_resize_pagecache(PAGECACHE *pagecache) +{ + DBUG_ENTER("ha_resize_pagecache"); + + if (pagecache->inited) + { + pthread_mutex_lock(&LOCK_global_system_variables); + long tmp_buff_size= (long) pagecache->param_buff_size; + long tmp_block_size= (long) pagecache->param_block_size; + uint division_limit= pagecache->param_division_limit; + uint age_threshold= pagecache->param_age_threshold; + pthread_mutex_unlock(&LOCK_global_system_variables); + DBUG_RETURN(!resize_pagecache(pagecache, tmp_block_size, + tmp_buff_size, + division_limit, age_threshold)); + } + DBUG_RETURN(0); +} +*/ + + +/* Change parameters for key cache (like size) */ + +int ha_change_pagecache_param(PAGECACHE *pagecache) +{ + if (pagecache->inited) + { + pthread_mutex_lock(&LOCK_global_system_variables); + uint division_limit= pagecache->param_division_limit; + uint age_threshold= pagecache->param_age_threshold; + pthread_mutex_unlock(&LOCK_global_system_variables); + change_pagecache_param(pagecache, division_limit, age_threshold); + } + return 0; +} + +/* Free memory allocated by a key cache */ + +int ha_end_pagecache(PAGECACHE *pagecache) +{ + end_pagecache(pagecache, 1); // Can never fail + return 0; +} + +/* Move all tables from one key cache to another one */ + +int ha_change_pagecache(PAGECACHE *old_pagecache, + PAGECACHE *new_pagecache) +{ + maria_change_pagecache(old_pagecache, new_pagecache); + return 0; +} + +#endif /* WITH_MARIA_STORAGE_ENGINE */ + /* Try to discover one table from handler(s) diff --git a/sql/handler.h b/sql/handler.h index 17e98803209..552e506ac4c 100644 --- a/sql/handler.h +++ b/sql/handler.h @@ -24,6 +24,7 @@ #include <my_handler.h> #include <ft_global.h> #include <keycache.h> +#include <pagecache.h> #ifndef NO_HASH #define NO_HASH /* Not yet implemented */ @@ -823,7 +824,8 @@ typedef struct st_ha_check_opt ulong sort_buffer_size; uint flags; /* isam layer flags (e.g. for myisamchk) */ uint sql_flags; /* sql layer flags - for something myisamchk cannot do */ - KEY_CACHE *key_cache; /* new key cache when changing key cache */ + KEY_CACHE *key_cache; /* new key cache when changing key cache */ + PAGECACHE *pagecache; /* new pagecache when changing pagecache */ void init(); } HA_CHECK_OPT; @@ -1694,6 +1696,15 @@ int ha_resize_key_cache(KEY_CACHE *key_cache); int ha_change_key_cache_param(KEY_CACHE *key_cache); int ha_change_key_cache(KEY_CACHE *old_key_cache, KEY_CACHE *new_key_cache); int ha_end_key_cache(KEY_CACHE *key_cache); +/* pagecache */ +int ha_init_pagecache(const char *name, PAGECACHE *pagecache); +/* +TODO: uncomment when resizing will be implemented +int ha_resize_pagecache(PAGECACHE *pagecache); +*/ +int ha_change_pagecache_param(PAGECACHE *pagecache); +int ha_change_pagecache(PAGECACHE *old_pagecache, PAGECACHE *new_pagecache); +int ha_end_pagecache(PAGECACHE *pagecache); /* report to InnoDB that control passes to the client */ int ha_release_temporary_latches(THD *thd); diff --git a/sql/mysql_priv.h b/sql/mysql_priv.h index 82e71f59b2c..f6cfa52f006 100644 --- a/sql/mysql_priv.h +++ b/sql/mysql_priv.h @@ -1629,6 +1629,9 @@ extern pthread_cond_t COND_global_read_lock; extern pthread_attr_t connection_attrib; extern I_List<THD> threads; extern I_List<NAMED_LIST> key_caches; +#ifdef WITH_MARIA_STORAGE_ENGINE +extern I_List<NAMED_LIST> pagecaches; +#endif /* WITH_MARIA_STORAGE_ENGINE */ extern MY_BITMAP temp_pool; extern String my_empty_string; extern const String my_null_string; diff --git a/sql/mysqld.cc b/sql/mysqld.cc index d3cada2405f..3fae670a579 100644 --- a/sql/mysqld.cc +++ b/sql/mysqld.cc @@ -551,6 +551,9 @@ FILE *stderror_file=0; I_List<THD> threads; I_List<NAMED_LIST> key_caches; +#ifdef WITH_MARIA_STORAGE_ENGINE +I_List<NAMED_LIST> pagecaches; +#endif /* WITH_MARIA_STORAGE_ENGINE */ Rpl_filter* rpl_filter; Rpl_filter* binlog_filter; @@ -1209,7 +1212,13 @@ void clean_up(bool print_message) tc_log->close(); xid_cache_free(); delete_elements(&key_caches, (void (*)(const char*, gptr)) free_key_cache); +#ifdef WITH_MARIA_STORAGE_ENGINE + delete_elements(&pagecaches, (void (*)(const char*, gptr)) free_pagecache); +#endif /* WITH_MARIA_STORAGE_ENGINE */ multi_keycache_free(); +#ifdef WITH_MARIA_STORAGE_ENGINE + multi_pagecache_free(); +#endif free_status_vars(); end_thr_alarm(1); /* Free allocated memory */ my_free_open_file_info(); @@ -2105,6 +2114,10 @@ the problem, but since we have already crashed, something is definitely wrong\n\ and this may fail.\n\n"); fprintf(stderr, "key_buffer_size=%lu\n", (ulong) dflt_key_cache->key_cache_mem_size); +#ifdef WITH_MARIA_STORAGE_ENGINE + fprintf(stderr, "page_buffer_size=%lu\n", + (ulong) dflt_pagecache->mem_size); +#endif /* WITH_MARIA_STORAGE_ENGINE */ fprintf(stderr, "read_buffer_size=%ld\n", (long) global_system_variables.read_buff_size); fprintf(stderr, "max_used_connections=%lu\n", max_used_connections); fprintf(stderr, "max_connections=%lu\n", max_connections); @@ -2112,6 +2125,9 @@ and this may fail.\n\n"); fprintf(stderr, "It is possible that mysqld could use up to \n\ key_buffer_size + (read_buffer_size + sort_buffer_size)*max_connections = %lu K\n\ bytes of memory\n", ((ulong) dflt_key_cache->key_cache_mem_size + +#ifdef WITH_MARIA_STORAGE_ENGINE + (ulong) dflt_pagecache->mem_size + +#endif /* WITH_MARIA_STORAGE_ENGINE */ (global_system_variables.read_buff_size + global_system_variables.sortbuff_size) * max_connections)/ 1024); @@ -2667,6 +2683,16 @@ static int init_common_variables(const char *conf_file_name, int argc, get_options(argc,argv); set_server_version(); +#ifdef WITH_MARIA_STORAGE_ENGINE + if (!(dflt_pagecache= get_or_create_pagecache(maria_pagecache_base.str, + maria_pagecache_base.length))) + exit(1); +/* + maria_pagecache->param_buff_size= maria_pagecache_var.param_buff_size; + maria_pagecache->param_block_size= maria_block_size; +*/ +#endif + DBUG_PRINT("info",("%s Ver %s for %s on %s\n",my_progname, server_version, SYSTEM_TYPE,MACHINE_TYPE)); @@ -3345,6 +3371,9 @@ server."); /* call ha_init_key_cache() on all key caches to init them */ process_key_caches(&ha_init_key_cache); +#ifdef WITH_MARIA_STORAGE_ENGINE + process_pagecaches(&ha_init_pagecache); +#endif /* WITH_MARIA_STORAGE_ENGINE */ #if defined(HAVE_MLOCKALL) && defined(MCL_CURRENT) && !defined(EMBEDDED_LIBRARY) if (locked_in_memory && !getuid()) @@ -5949,7 +5978,7 @@ log and this option does nothing anymore.", "this to get better index handling (for all reads and multiple writes) to " "as much as you can afford; 64M on a 256M machine that mainly runs MySQL " "is quite common.", - (gptr*) &maria_key_cache_var.param_buff_size, (gptr*) 0, + (gptr*) &maria_pagecache_var.param_buff_size, (gptr*) 0, 0, (GET_ULL | GET_ASK_ADDR), REQUIRED_ARG, KEY_CACHE_SIZE, MALLOC_OVERHEAD, ~(ulong) 0, MALLOC_OVERHEAD, IO_SIZE, 0}, @@ -6143,6 +6172,33 @@ The minimum value for this variable is 4096.", (gptr*) &global_system_variables.optimizer_search_depth, (gptr*) &max_system_variables.optimizer_search_depth, 0, GET_ULONG, OPT_ARG, MAX_TABLES+1, 0, MAX_TABLES+2, 0, 1, 0}, +#ifdef WITH_MARIA_STORAGE_ENGINE + {"pagecache_age_threshold", OPT_KEY_CACHE_AGE_THRESHOLD, + "This characterizes the number of hits a hot block has to be untouched until it is considered aged enough to be downgraded to a warm block. This specifies the percentage ratio of that number of hits to the total number of blocks in key cache", + (gptr*) &dflt_pagecache_var.param_age_threshold, + (gptr*) 0, + 0, (GET_ULONG | GET_ASK_ADDR), REQUIRED_ARG, + 300, 100, ~0L, 0, 100, 0}, + {"pagecache_block_size", OPT_KEY_CACHE_BLOCK_SIZE, + "The default size of key cache blocks", + (gptr*) &dflt_pagecache_var.param_block_size, + (gptr*) 0, + 0, (GET_ULONG | GET_ASK_ADDR), REQUIRED_ARG, + KEY_CACHE_BLOCK_SIZE , 512, 1024*16, MALLOC_OVERHEAD, 512, 0}, + {"pagecache_buffer_size", OPT_KEY_BUFFER_SIZE, + "The size of the buffer used for index blocks for MyISAM tables. Increase this to get better index handling (for all reads and multiple writes) to as much as you can afford; 64M on a 256M machine that mainly runs MySQL is quite common.", + (gptr*) &dflt_pagecache_var.param_buff_size, + (gptr*) 0, + 0, (GET_ULL | GET_ASK_ADDR), + REQUIRED_ARG, KEY_CACHE_SIZE, MALLOC_OVERHEAD, ~(ulong) 0, MALLOC_OVERHEAD, + IO_SIZE, 0}, + {"pagecache_division_limit", OPT_KEY_CACHE_DIVISION_LIMIT, + "The minimum percentage of warm blocks in key cache", + (gptr*) &dflt_pagecache_var.param_division_limit, + (gptr*) 0, + 0, (GET_ULONG | GET_ASK_ADDR) , REQUIRED_ARG, 100, + 1, 100, 0, 1, 0}, +#endif /* WITH_MARIA_STORAGE_ENGINE */ {"plugin_dir", OPT_PLUGIN_DIR, "Directory for plugins.", (gptr*) &opt_plugin_dir_ptr, (gptr*) &opt_plugin_dir_ptr, 0, @@ -7035,20 +7091,21 @@ static void mysql_init_variables(void) threads.empty(); thread_cache.empty(); key_caches.empty(); +#ifdef WITH_MARIA_STORAGE_ENGINE + pagecaches.empty(); +#endif /* WITH_MARIA_STORAGE_ENGINE */ if (!(dflt_key_cache= get_or_create_key_cache(default_key_cache_base.str, default_key_cache_base.length))) exit(1); -#ifdef WITH_MARIA_STORAGE_ENGINE - if (!(maria_key_cache= get_or_create_key_cache(maria_key_cache_base.str, - maria_key_cache_base.length))) - exit(1); - maria_key_cache->param_buff_size= maria_key_cache_var.param_buff_size; - maria_key_cache->param_block_size= maria_block_size; -#endif - /* set key_cache_hash.default_value = dflt_key_cache */ + /* set key_cache_hash.default_value = dflt_key_cache */ multi_keycache_init(); +#ifdef WITH_MARIA_STORAGE_ENGINE + /* set pagecache_hash.default_value = dflt_pagecache */ + multi_pagecache_init(); +#endif + /* Set directory paths */ strmake(language, LANGUAGE, sizeof(language)-1); strmake(mysql_real_data_home, get_relative_path(DATADIR), @@ -8168,6 +8225,9 @@ void refresh_status(THD *thd) /* Reset the counters of all key caches (default and named). */ process_key_caches(reset_key_cache_counters); +#ifdef WITH_MARIA_STORAGE_ENGINE + process_pagecaches(reset_pagecache_counters); +#endif /* WITH_MARIA_STORAGE_ENGINE */ pthread_mutex_unlock(&LOCK_status); /* diff --git a/sql/set_var.cc b/sql/set_var.cc index bd68863ff97..5dd438ba95a 100644 --- a/sql/set_var.cc +++ b/sql/set_var.cc @@ -156,6 +156,9 @@ static void fix_thd_mem_root(THD *thd, enum_var_type type); static void fix_trans_mem_root(THD *thd, enum_var_type type); static void fix_server_id(THD *thd, enum_var_type type); static KEY_CACHE *create_key_cache(const char *name, uint length); +#ifdef WITH_MARIA_STORAGE_ENGINE +static PAGECACHE *create_pagecache(const char *name, uint length); +#endif /* WITH_MARIA_STORAGE_ENGINE */ void fix_sql_mode_var(THD *thd, enum_var_type type); static byte *get_error_count(THD *thd); static byte *get_warning_count(THD *thd); @@ -258,6 +261,14 @@ sys_var_key_cache_long sys_key_cache_division_limit("key_cache_division_limit", sys_var_key_cache_long sys_key_cache_age_threshold("key_cache_age_threshold", offsetof(KEY_CACHE, param_age_threshold)); +#ifdef WITH_MARIA_STORAGE_ENGINE +sys_var_pagecache_long sys_pagecache_division_limit("pagecache_division_limit", + offsetof(PAGECACHE, + param_division_limit)); +sys_var_pagecache_long sys_pagecache_age_threshold("pagecache_age_threshold", + offsetof(KEY_CACHE, + param_age_threshold)); +#endif /* WITH_MARIA_STORAGE_ENGINE */ sys_var_bool_ptr sys_local_infile("local_infile", &opt_local_infile); sys_var_trust_routine_creators @@ -855,6 +866,12 @@ SHOW_VAR init_vars[]= { SHOW_SYS}, {sys_key_cache_division_limit.name, (char*) &sys_key_cache_division_limit, SHOW_SYS}, +#ifdef WITH_MARIA_STORAGE_ENGINE + {sys_pagecache_age_threshold.name, (char*) &sys_pagecache_age_threshold, + SHOW_SYS}, + {sys_pagecache_division_limit.name, (char*) &sys_pagecache_division_limit, + SHOW_SYS}, +#endif /* WITH_MARIA_STORAGE_ENGINE */ {"language", language, SHOW_CHAR}, {"large_files_support", (char*) &opt_large_files, SHOW_BOOL}, {"large_page_size", (char*) &opt_large_page_size, SHOW_INT}, @@ -2396,10 +2413,13 @@ void sys_var_collation_server::set_default(THD *thd, enum_var_type type) LEX_STRING default_key_cache_base= {(char *) "default", 7 }; -LEX_STRING maria_key_cache_base= {(char *) "maria", 5 }; - static KEY_CACHE zero_key_cache; +#ifdef WITH_MARIA_STORAGE_ENGINE +LEX_STRING maria_pagecache_base= {(char *) "default", 7 }; +static PAGECACHE zero_pagecache; +#endif /* WITH_MARIA_STORAGE_ENGINE */ + KEY_CACHE *get_key_cache(LEX_STRING *cache_name) { safe_mutex_assert_owner(&LOCK_global_system_variables); @@ -2410,6 +2430,18 @@ KEY_CACHE *get_key_cache(LEX_STRING *cache_name) } +#ifdef WITH_MARIA_STORAGE_ENGINE +PAGECACHE *get_pagecache(LEX_STRING *cache_name) +{ + safe_mutex_assert_owner(&LOCK_global_system_variables); + if (!cache_name || ! cache_name->length) + cache_name= &default_key_cache_base; + return ((PAGECACHE*) find_named(&pagecaches, + cache_name->str, cache_name->length, 0)); +} +#endif /* WITH_MARIA_STORAGE_ENGINE */ + + byte *sys_var_key_cache_param::value_ptr(THD *thd, enum_var_type type, LEX_STRING *base) { @@ -2420,6 +2452,18 @@ byte *sys_var_key_cache_param::value_ptr(THD *thd, enum_var_type type, } +#ifdef WITH_MARIA_STORAGE_ENGINE +byte *sys_var_pagecache_param::value_ptr(THD *thd, enum_var_type type, + LEX_STRING *base) +{ + PAGECACHE *pagecache= get_pagecache(base); + if (!pagecache) + pagecache= &zero_pagecache; + return (byte*) pagecache + offset ; +} +#endif /* WITH_MARIA_STORAGE_ENGINE */ + + bool sys_var_key_buffer_size::update(THD *thd, set_var *var) { ulonglong tmp= var->save_result.ulonglong_value; @@ -2556,6 +2600,60 @@ end: } +#ifdef WITH_MARIA_STORAGE_ENGINE +bool sys_var_pagecache_long::update(THD *thd, set_var *var) +{ + ulong tmp= (ulong) var->value->val_int(); + LEX_STRING *base_name= &var->base; + bool error= 0; + + if (!base_name->length) + base_name= &maria_pagecache_base; + + pthread_mutex_lock(&LOCK_global_system_variables); + PAGECACHE *pagecache= get_pagecache(base_name); + + if (!pagecache && !(pagecache= create_pagecache(base_name->str, + base_name->length))) + { + error= 1; + goto end; + } + + /* + Abort if some other thread is changing the key cache + TODO: This should be changed so that we wait until the previous + assignment is done and then do the new assign + */ + if (pagecache->in_init) + goto end; + + *((ulong*) (((char*) pagecache) + offset))= + (ulong) getopt_ull_limit_value(tmp, option_limits); + + /* + Don't create a new key cache if it didn't exist + (pagecaches are created only when the user sets block_size) + */ + pagecache->in_init= 1; + + pthread_mutex_unlock(&LOCK_global_system_variables); + + /* + TODO: uncomment whan it will be implemented + error= (bool) (ha_resize_pagecache(pagecache)); + */ + + pthread_mutex_lock(&LOCK_global_system_variables); + pagecache->in_init= 0; + +end: + pthread_mutex_unlock(&LOCK_global_system_variables); + return error; +} +#endif /* WITH_MARIA_STORAGE_ENGINE */ + + bool sys_var_log_state::update(THD *thd, set_var *var) { bool res= 0; @@ -3872,12 +3970,86 @@ bool process_key_caches(int (* func) (const char *name, KEY_CACHE *)) } +#ifdef WITH_MARIA_STORAGE_ENGINE + +static PAGECACHE *create_pagecache(const char *name, uint length) +{ + PAGECACHE *pagecache; + DBUG_ENTER("create_pagecache"); + DBUG_PRINT("enter",("name: %.*s", length, name)); + + if ((pagecache= (PAGECACHE*) my_malloc(sizeof(PAGECACHE), + MYF(MY_ZEROFILL | MY_WME)))) + { + if (!new NAMED_LIST(&pagecaches, name, length, (gptr) pagecache)) + { + my_free((char*) pagecache, MYF(0)); + pagecache= 0; + } + else + { + /* + Set default values for a key cache + The values in dflt_pagecache_var is set by my_getopt() at startup + We don't set 'buff_size' as this is used to enable the key cache + */ + pagecache->param_buff_size= (dflt_pagecache_var.param_buff_size ? + dflt_pagecache_var.param_buff_size: + KEY_CACHE_SIZE); + pagecache->param_block_size= dflt_pagecache_var.param_block_size; + pagecache->param_division_limit= dflt_pagecache_var.param_division_limit; + pagecache->param_age_threshold= dflt_pagecache_var.param_age_threshold; + } + } + DBUG_RETURN(pagecache); +} + + +PAGECACHE *get_or_create_pagecache(const char *name, uint length) +{ + LEX_STRING pagecache_name; + PAGECACHE *pagecache; + + pagecache_name.str= (char *) name; + pagecache_name.length= length; + pthread_mutex_lock(&LOCK_global_system_variables); + if (!(pagecache= get_pagecache(&pagecache_name))) + pagecache= create_pagecache(name, length); + pthread_mutex_unlock(&LOCK_global_system_variables); + return pagecache; +} + + +void free_pagecache(const char *name, PAGECACHE *pagecache) +{ + ha_end_pagecache(pagecache); + my_free((char*) pagecache, MYF(0)); +} + + +bool process_pagecaches(int (* func) (const char *name, PAGECACHE *)) +{ + I_List_iterator<NAMED_LIST> it(pagecaches); + NAMED_LIST *element; + + while ((element= it++)) + { + PAGECACHE *pagecache= (PAGECACHE *) element->data; + func(element->name, pagecache); + } + return 0; +} + +#endif /* WITH_MARIA_STORAGE_ENGINE */ + + void sys_var_trust_routine_creators::warn_deprecated(THD *thd) { WARN_DEPRECATED(thd, "5.2", "log_bin_trust_routine_creators", "'log_bin_trust_function_creators'"); } + void sys_var_trust_routine_creators::set_default(THD *thd, enum_var_type type) { warn_deprecated(thd); diff --git a/sql/set_var.h b/sql/set_var.h index 17f9b248c07..a415f629cb9 100644 --- a/sql/set_var.h +++ b/sql/set_var.h @@ -749,6 +749,33 @@ public: }; +#ifdef WITH_MARIA_STORAGE_ENGINE +class sys_var_pagecache_param :public sys_var +{ +protected: + size_t offset; +public: + sys_var_pagecache_param(const char *name_arg, size_t offset_arg) + :sys_var(name_arg), offset(offset_arg) + {} + byte *value_ptr(THD *thd, enum_var_type type, LEX_STRING *base); + bool check_default(enum_var_type type) { return 1; } + bool is_struct() { return 1; } +}; + + +class sys_var_pagecache_long :public sys_var_pagecache_param +{ +public: + sys_var_pagecache_long(const char *name_arg, size_t offset_arg) + :sys_var_pagecache_param(name_arg, offset_arg) + {} + bool update(THD *thd, set_var *var); + SHOW_TYPE type() { return SHOW_LONG; } +}; +#endif /* WITH_MARIA_STORAGE_ENGINE */ + + class sys_var_thd_date_time_format :public sys_var_thd { DATE_TIME_FORMAT *SV::*offset; @@ -1095,7 +1122,11 @@ public: my_free((char*) name, MYF(0)); } friend bool process_key_caches(int (* func) (const char *name, - KEY_CACHE *)); + KEY_CACHE *)); +#ifdef WITH_MARIA_STORAGE_ENGINE + friend bool process_pagecaches(int (* func) (const char *name, + PAGECACHE *)); +#endif /* WITH_MARIA_STORAGE_ENGINE */ friend void delete_elements(I_List<NAMED_LIST> *list, void (*free_element)(const char*, gptr)); }; @@ -1105,7 +1136,9 @@ public: extern sys_var_thd_bool sys_old_alter_table; extern sys_var_thd_bool sys_old_passwords; extern LEX_STRING default_key_cache_base; -extern LEX_STRING maria_key_cache_base; +#ifdef WITH_MARIA_STORAGE_ENGINE +extern LEX_STRING maria_pagecache_base; +#endif /* WITH_MARIA_STORAGE_ENGINE */ /* For sql_yacc */ struct sys_var_with_base @@ -1143,3 +1176,8 @@ void free_key_cache(const char *name, KEY_CACHE *key_cache); bool process_key_caches(int (* func) (const char *name, KEY_CACHE *)); void delete_elements(I_List<NAMED_LIST> *list, void (*free_element)(const char*, gptr)); +#ifdef WITH_MARIA_STORAGE_ENGINE +PAGECACHE *get_or_create_pagecache(const char *name, uint length); +void free_pagecache(const char *name, PAGECACHE *pagecache); +bool process_pagecaches(int (* func) (const char *name, PAGECACHE *)); +#endif /* WITH_MARIA_STORAGE_ENGINE */ diff --git a/storage/maria/Makefile.am b/storage/maria/Makefile.am index b6c713571d7..cacc88147a9 100644 --- a/storage/maria/Makefile.am +++ b/storage/maria/Makefile.am @@ -111,7 +111,8 @@ libmaria_a_SOURCES = ma_init.c ma_open.c ma_extra.c ma_info.c ma_rkey.c \ ma_ft_nlq_search.c ft_maria.c ma_sort.c \ ha_maria.cc trnman.c lockman.c tablockman.c \ ma_rt_index.c ma_rt_key.c ma_rt_mbr.c ma_rt_split.c \ - ma_sp_key.c ma_control_file.c ma_loghandler.c + ma_sp_key.c ma_control_file.c ma_loghandler.c \ + ma_pagecache.c ma_pagecaches.c CLEANFILES = test?.MA? FT?.MA? isam.log ma_test_all ma_rt_test.MA? sp_test.MA? SUFFIXES = .sh diff --git a/storage/maria/ha_maria.cc b/storage/maria/ha_maria.cc index 102f987f01a..cb64cf6f693 100644 --- a/storage/maria/ha_maria.cc +++ b/storage/maria/ha_maria.cc @@ -198,7 +198,7 @@ const char *ha_maria::index_type(uint key_number) #ifdef HAVE_REPLICATION int ha_maria::net_read_dump(NET * net) { - int data_fd= file->dfile; + int data_fd= file->dfile.file; int error= 0; my_seek(data_fd, 0L, MY_SEEK_SET, MYF(MY_WME)); @@ -231,7 +231,7 @@ int ha_maria::dump(THD * thd, int fd) NET *net= &thd->net; uint block_size= share->block_size; my_off_t bytes_to_read= share->state.state.data_file_length; - int data_fd= file->dfile; + int data_fd= file->dfile.file; byte *buf= (byte *) my_malloc(block_size, MYF(MY_WME)); if (!buf) return ENOMEM; @@ -424,7 +424,7 @@ int ha_maria::check(THD * thd, HA_CHECK_OPT * check_opt) { uint old_testflag= param.testflag; param.testflag |= T_MEDIUM; - if (!(error= init_io_cache(¶m.read_cache, file->dfile, + if (!(error= init_io_cache(¶m.read_cache, file->dfile.file, my_default_record_cache_size, READ_CACHE, share->pack.header_length, 1, MYF(MY_WME)))) { @@ -827,7 +827,7 @@ int ha_maria::repair(THD *thd, HA_CHECK ¶m, bool optimize) int ha_maria::assign_to_keycache(THD * thd, HA_CHECK_OPT *check_opt) { - KEY_CACHE *new_key_cache= check_opt->key_cache; + PAGECACHE *new_pagecache= check_opt->pagecache; const char *errmsg= 0; int error= HA_ADMIN_OK; ulonglong map= ~(ulonglong) 0; @@ -848,7 +848,7 @@ int ha_maria::assign_to_keycache(THD * thd, HA_CHECK_OPT *check_opt) map= kmap.to_ulonglong(); } - if ((error= maria_assign_to_key_cache(file, map, new_key_cache))) + if ((error= maria_assign_to_pagecache(file, map, new_pagecache))) { char buf[STRING_BUFFER_USUAL_SIZE]; my_snprintf(buf, sizeof(buf), diff --git a/storage/maria/ma_bitmap.c b/storage/maria/ma_bitmap.c index 5ed5a776658..1192396ca19 100644 --- a/storage/maria/ma_bitmap.c +++ b/storage/maria/ma_bitmap.c @@ -122,10 +122,13 @@ static inline my_bool write_changed_bitmap(MARIA_SHARE *share, MARIA_FILE_BITMAP *bitmap) { - return (key_cache_write(share->key_cache, - bitmap->file, bitmap->page * bitmap->block_size, 0, - (byte*) bitmap->map, - bitmap->block_size, bitmap->block_size, 1)); + DBUG_ASSERT(share->pagecache->block_size == bitmap->block_size); + return (pagecache_write(share->pagecache, + (PAGECACHE_FILE*)&bitmap->file, bitmap->page, 0, + (byte*) bitmap->map, PAGECACHE_PLAIN_PAGE, + PAGECACHE_LOCK_LEFT_UNLOCKED, + PAGECACHE_PIN_LEFT_PINNED, + PAGECACHE_WRITE_DELAY, 0)); } /* @@ -398,10 +401,12 @@ my_bool _ma_read_bitmap_page(MARIA_SHARE *share, MARIA_FILE_BITMAP *bitmap, DBUG_RETURN(0); } bitmap->used_size= bitmap->total_size; - res= key_cache_read(share->key_cache, - bitmap->file, position, 0, + DBUG_ASSERT(share->pagecache->block_size == bitmap->block_size); + res= pagecache_read(share->pagecache, + (PAGECACHE_FILE*)&bitmap->file, page, 0, (byte*) bitmap->map, - bitmap->block_size, bitmap->block_size, 0) == 0; + PAGECACHE_PLAIN_PAGE, + PAGECACHE_LOCK_LEFT_UNLOCKED, 0) == 0; #ifndef DBUG_OFF if (!res) memcpy(bitmap->map+ bitmap->block_size, bitmap->map, bitmap->block_size); diff --git a/storage/maria/ma_blockrec.c b/storage/maria/ma_blockrec.c index f1345b2c2f3..f1a1df23358 100644 --- a/storage/maria/ma_blockrec.c +++ b/storage/maria/ma_blockrec.c @@ -342,7 +342,7 @@ my_bool _ma_once_init_block_row(MARIA_SHARE *share, File data_file) my_bool _ma_once_end_block_row(MARIA_SHARE *share) { int res= _ma_bitmap_end(share); - if (flush_key_blocks(share->key_cache, share->bitmap.file, + if (flush_pagecache_blocks(share->pagecache, (PAGECACHE_FILE*)&share->bitmap, share->temporary ? FLUSH_IGNORE_CHANGED : FLUSH_RELEASE)) res= 1; @@ -845,11 +845,14 @@ static my_bool get_head_or_tail_page(MARIA_HA *info, else { byte *dir; + /* TODO: lock the page */ /* Read old page */ - if (!(res->buff= key_cache_read(info->s->key_cache, - info->dfile, - (my_off_t) block->page * block_size, 0, - buff, block_size, block_size, 0))) + DBUG_ASSERT(info->s->pagecache->block_size == block_size); + if (!(res->buff= pagecache_read(info->s->pagecache, + &info->dfile, + (my_off_t) block->page, 0, + buff, PAGECACHE_PLAIN_PAGE, + PAGECACHE_LOCK_LEFT_UNLOCKED, 0))) DBUG_RETURN(1); DBUG_ASSERT((res->buff[PAGE_TYPE_OFFSET] & PAGE_TYPE_MASK) == page_type); if (!(dir= find_free_position(buff, block_size, &res->offset, @@ -912,6 +915,7 @@ static my_bool write_tail(MARIA_HA *info, (ulong) block->page, length)); info->keybuff_used= 1; + /* page will be pinned & locked by get_head_or_tail_page */ if (get_head_or_tail_page(info, block, info->keyread_buff, length, TAIL_PAGE, &row_pos)) DBUG_RETURN(1); @@ -936,9 +940,15 @@ static my_bool write_tail(MARIA_HA *info, position= (my_off_t) block->page * block_size; if (info->state->data_file_length <= position) info->state->data_file_length= position + block_size; - DBUG_RETURN(key_cache_write(share->key_cache, - info->dfile, position, 0, - row_pos.buff, block_size, block_size, 1)); + /* TODO: left the page pinned (or pin it if it is new) and unlock\ + the page (do not lock if it is new */ + DBUG_ASSERT(share->pagecache->block_size == block_size); + DBUG_RETURN(pagecache_write(share->pagecache, + &info->dfile, block->page, 0, + row_pos.buff,PAGECACHE_PLAIN_PAGE, + PAGECACHE_LOCK_LEFT_UNLOCKED, + PAGECACHE_PIN_LEFT_PINNED, + PAGECACHE_WRITE_DELAY, 0)); } @@ -969,7 +979,7 @@ static my_bool write_full_pages(MARIA_HA *info, DBUG_PRINT("enter", ("length: %lu page: %lu page_count: %lu", (ulong) length, (ulong) block->page, (ulong) block->page_count)); - + info->keybuff_used= 1; page= block->page; page_count= block->page_count; @@ -1001,9 +1011,18 @@ static my_bool write_full_pages(MARIA_HA *info, memcpy(buff + LSN_SIZE + PAGE_TYPE_SIZE, data, copy_length); length-= copy_length; - if (key_cache_write(share->key_cache, - info->dfile, (my_off_t) page * block_size, 0, - buff, block_size, block_size, 1)) + /* + TODO: replace PAGECACHE_PLAIN_PAGE with PAGECACHE_LSN_PAGE when + LSN on the pages will be implemented + */ + DBUG_ASSERT(share->pagecache->block_size == block_size); + if (pagecache_write(share->pagecache, + &info->dfile, page, 0, + buff, PAGECACHE_PLAIN_PAGE, + PAGECACHE_LOCK_LEFT_UNLOCKED, + PAGECACHE_PIN_LEFT_PINNED, + PAGECACHE_WRITE_DELAY, + 0)) DBUG_RETURN(1); page++; block->used= BLOCKUSED_USED; @@ -1133,7 +1152,7 @@ static my_bool write_block_record(MARIA_HA *info, const byte *record, To avoid double copying of data, we copy as many columns that fits into the page. The rest goes into info->packed_row. - Using an extra buffer, instead of doing continous writes to different + Using an extra buffer, instead of doing continuous writes to different pages, uses less code and we don't need to have to do a complex call for every data segment we want to store. */ @@ -1363,14 +1382,14 @@ static my_bool write_block_record(MARIA_HA *info, const byte *record, - Bitmap code allocated a tail page we don't need. - The last full page allocated needs to be changed to a tail page (Because we put more data than we thought on the head page) - - The reserved pages in bitmap_blocks for the main page has one of + + The reserved pages in bitmap_blocks for the main page has one of the following allocations: - Full pages, with following blocks: # * full pages empty page ; To be used if we change last full to tail page. This has 'count' = 0. - tail page (optional, if last full page was part full) + tail page (optional, if last full page was part full) - One tail page */ @@ -1485,9 +1504,13 @@ static my_bool write_block_record(MARIA_HA *info, const byte *record, position= (my_off_t) head_block->page * block_size; if (info->state->data_file_length <= position) info->state->data_file_length= position + block_size; - if (key_cache_write(share->key_cache, - info->dfile, position, 0, - page_buff, share->block_size, share->block_size, 1)) + DBUG_ASSERT(share->pagecache->block_size == block_size); + if (pagecache_write(share->pagecache, + &info->dfile, head_block->page, 0, + page_buff, PAGECACHE_PLAIN_PAGE, + PAGECACHE_LOCK_LEFT_UNLOCKED, + PAGECACHE_PIN_LEFT_PINNED, + PAGECACHE_WRITE_DELAY, 0)) goto disk_err; if (tmp_data_used) @@ -1557,7 +1580,8 @@ MARIA_RECORD_POS _ma_write_init_block_record(MARIA_HA *info, calc_record_size(info, record, &info->cur_row); if (_ma_bitmap_find_place(info, &info->cur_row, blocks)) - DBUG_RETURN(HA_OFFSET_ERROR); /* Error reding bitmap */ + DBUG_RETURN(HA_OFFSET_ERROR); /* Error reading bitmap */ + /* page will be pinned & locked by get_head_or_tail_page */ if (get_head_or_tail_page(info, blocks->block, info->buff, info->s->base.min_row_length, HEAD_PAGE, &row_pos)) DBUG_RETURN(HA_OFFSET_ERROR); @@ -1665,9 +1689,11 @@ my_bool _ma_update_block_record(MARIA_HA *info, MARIA_RECORD_POS record_pos, calc_record_size(info, record, new_row); page= ma_recordpos_to_page(record_pos); - if (!(buff= key_cache_read(info->s->key_cache, - info->dfile, (my_off_t) page * block_size, 0, - info->buff, block_size, block_size, 0))) + DBUG_ASSERT(info->s->pagecache->block_size == block_size); + if (!(buff= pagecache_read(info->s->pagecache, + &info->dfile, (my_off_t) page, 0, + info->buff, PAGECACHE_PLAIN_PAGE, + PAGECACHE_LOCK_LEFT_UNLOCKED, 0))) DBUG_RETURN(1); org_empty_size= uint2korr(buff + EMPTY_SPACE_OFFSET); rownr= ma_recordpos_to_offset(record_pos); @@ -1779,14 +1805,15 @@ static my_bool delete_head_or_tail(MARIA_HA *info, uint number_of_records, empty_space, length; uint block_size= share->block_size; byte *buff, *dir; - my_off_t position; DBUG_ENTER("delete_head_or_tail"); info->keybuff_used= 1; - if (!(buff= key_cache_read(share->key_cache, - info->dfile, page * block_size, 0, + DBUG_ASSERT(info->s->pagecache->block_size == block_size); + if (!(buff= pagecache_read(share->pagecache, + &info->dfile, page, 0, info->keyread_buff, - block_size, block_size, 0))) + PAGECACHE_PLAIN_PAGE, + PAGECACHE_LOCK_LEFT_UNLOCKED, 0))) DBUG_RETURN(1); number_of_records= (uint) ((uchar *) buff)[DIR_ENTRY_OFFSET]; @@ -1825,10 +1852,13 @@ static my_bool delete_head_or_tail(MARIA_HA *info, { int2store(buff + EMPTY_SPACE_OFFSET, empty_space); buff[PAGE_TYPE_OFFSET]|= (byte) PAGE_CAN_BE_COMPACTED; - position= (my_off_t) page * block_size; - if (key_cache_write(share->key_cache, - info->dfile, position, 0, - buff, block_size, block_size, 1)) + DBUG_ASSERT(share->pagecache->block_size == block_size); + if (pagecache_write(share->pagecache, + &info->dfile, page, 0, + buff, PAGECACHE_PLAIN_PAGE, + PAGECACHE_LOCK_LEFT_UNLOCKED, + PAGECACHE_PIN_LEFT_PINNED, + PAGECACHE_WRITE_DELAY, 0)) DBUG_RETURN(1); } else @@ -2032,10 +2062,11 @@ static byte *read_next_extent(MARIA_HA *info, MARIA_EXTENT_CURSOR *extent, info->cur_row.empty_bits= info->cur_row.empty_bits_buffer; } - if (!(buff= key_cache_read(share->key_cache, - info->dfile, extent->page * share->block_size, 0, - info->buff, - share->block_size, share->block_size, 0))) + DBUG_ASSERT(share->pagecache->block_size == share->block_size); + if (!(buff= pagecache_read(share->pagecache, + &info->dfile, extent->page, 0, + info->buff, PAGECACHE_PLAIN_PAGE, + PAGECACHE_LOCK_LEFT_UNLOCKED, 0))) { /* check if we tried to read over end of file (ie: bad data in record) */ if ((extent->page + 1) * share->block_size > info->state->data_file_length) @@ -2441,18 +2472,18 @@ int _ma_read_block_record(MARIA_HA *info, byte *record, MARIA_RECORD_POS record_pos) { byte *data, *end_of_data, *buff; - my_off_t page; uint offset; uint block_size= info->s->block_size; DBUG_ENTER("_ma_read_block_record"); DBUG_PRINT("enter", ("rowid: %lu", (long) record_pos)); - page= ma_recordpos_to_page(record_pos) * block_size; offset= ma_recordpos_to_offset(record_pos); - - if (!(buff= key_cache_read(info->s->key_cache, - info->dfile, page, 0, info->buff, - block_size, block_size, 1))) + + DBUG_ASSERT(info->s->pagecache->block_size == block_size); + if (!(buff= pagecache_read(info->s->pagecache, + &info->dfile, ma_recordpos_to_page(record_pos), 0, + info->buff, PAGECACHE_PLAIN_PAGE, + PAGECACHE_LOCK_LEFT_UNLOCKED, 0))) DBUG_RETURN(1); DBUG_ASSERT((buff[PAGE_TYPE_OFFSET] & PAGE_TYPE_MASK) == HEAD_PAGE); if (!(data= get_record_position(buff, block_size, offset, &end_of_data))) @@ -2639,11 +2670,11 @@ restart_bitmap_scan: page= (info->scan.bitmap_page + 1 + (data - info->scan.bitmap_buff) / 6 * 16 + bit_pos - 1); info->scan.row_base_page= ma_recordpos(page, 0); - if (!(key_cache_read(info->s->key_cache, - info->dfile, - (my_off_t) page * block_size, - 0, info->scan.page_buff, - block_size, block_size, 0))) + if (!(pagecache_read(info->s->pagecache, + &info->dfile, + page, 0, info->scan.page_buff, + PAGECACHE_PLAIN_PAGE, + PAGECACHE_LOCK_LEFT_UNLOCKED, 0))) DBUG_RETURN(my_errno); if (((info->scan.page_buff[PAGE_TYPE_OFFSET] & PAGE_TYPE_MASK) != HEAD_PAGE) || @@ -2679,8 +2710,10 @@ restart_bitmap_scan: { DBUG_RETURN((my_errno= HA_ERR_END_OF_FILE)); } - if (!(key_cache_read(info->s->key_cache, info->dfile, filepos, - 0, info->scan.bitmap_buff, block_size, block_size, 0))) + if (!(pagecache_read(info->s->pagecache, &info->dfile, + info->scan.bitmap_page, + 0, info->scan.bitmap_buff, PAGECACHE_PLAIN_PAGE, + PAGECACHE_LOCK_LEFT_UNLOCKED, 0))) DBUG_RETURN(my_errno); /* Skip scanning 'bits' in bitmap scan code */ info->scan.bitmap_pos= info->scan.bitmap_buff - 6; diff --git a/storage/maria/ma_check.c b/storage/maria/ma_check.c index ccce19de994..98c3d56000a 100644 --- a/storage/maria/ma_check.c +++ b/storage/maria/ma_check.c @@ -104,7 +104,7 @@ void maria_chk_init(HA_CHECK *param) param->myf_rw=MYF(MY_NABP | MY_WME | MY_WAIT_IF_FULL); param->start_check_pos=0; param->max_record_length= LONGLONG_MAX; - param->key_cache_block_size= KEY_CACHE_BLOCK_SIZE; + param->pagecache_block_size= KEY_CACHE_BLOCK_SIZE; param->stats_method= MI_STATS_METHOD_NULLS_NOT_EQUAL; } @@ -175,7 +175,7 @@ int maria_chk_del(HA_CHECK *param, register MARIA_HA *info, uint test_flag) printf(" %9s",llstr(next_link,buff)); if (next_link >= info->state->data_file_length) goto wrong; - if (my_pread(info->dfile,(char*) buff,delete_link_length, + if (my_pread(info->dfile.file, (char*) buff, delete_link_length, next_link,MYF(MY_NABP))) { if (test_flag & T_VERBOSE) puts(""); @@ -287,10 +287,13 @@ static int check_k_link(HA_CHECK *param, register MARIA_HA *info, /* purecov: end */ } - if (!(buff=key_cache_read(info->s->key_cache, - info->s->kfile, next_link, DFLT_INIT_HITS, - (byte*) info->buff, - block_size, block_size, 1))) + DBUG_ASSERT(info->s->pagecache->block_size == block_size); + if (!(buff= pagecache_read(info->s->pagecache, + &info->s->kfile, next_link/block_size, + DFLT_INIT_HITS, + (byte*) info->buff, + PAGECACHE_PLAIN_PAGE, + PAGECACHE_LOCK_LEFT_UNLOCKED, 0))) { /* purecov: begin tested */ _ma_check_print_error(param, "key cache read error for block: %s", @@ -326,10 +329,10 @@ int maria_chk_size(HA_CHECK *param, register MARIA_HA *info) puts("- check file-size"); /* The following is needed if called externally (not from maria_chk) */ - flush_key_blocks(info->s->key_cache, - info->s->kfile, FLUSH_FORCE_WRITE); + flush_pagecache_blocks(info->s->pagecache, + &info->s->kfile, FLUSH_FORCE_WRITE); - size=my_seek(info->s->kfile,0L,MY_SEEK_END,MYF(0)); + size= my_seek(info->s->kfile.file, 0L, MY_SEEK_END, MYF(0)); if ((skr=(my_off_t) info->state->key_file_length) != size) { /* Don't give error if file generated by mariapack */ @@ -353,7 +356,7 @@ int maria_chk_size(HA_CHECK *param, register MARIA_HA *info) llstr(info->state->key_file_length,buff), llstr(info->s->base.max_key_file_length-1,buff)); - size=my_seek(info->dfile,0L,MY_SEEK_END,MYF(0)); + size= my_seek(info->dfile.file, 0L, MY_SEEK_END, MYF(0)); skr=(my_off_t) info->state->data_file_length; if (info->s->options & HA_OPTION_COMPRESS_RECORD) skr+= MEMMAP_EXTRA_MARGIN; @@ -588,7 +591,7 @@ static int chk_index_down(HA_CHECK *param, MARIA_HA *info, { /* purecov: begin tested */ /* Give it a chance to fit in the real file size. */ - my_off_t max_length= my_seek(info->s->kfile, 0L, MY_SEEK_END, MYF(0)); + my_off_t max_length= my_seek(info->s->kfile.file, 0L, MY_SEEK_END, MYF(0)); _ma_check_print_error(param, "Invalid key block position: %s " "key block size: %u file_length: %s", llstr(page, llbuff), keyinfo->block_length, @@ -1920,10 +1923,10 @@ int maria_repair(HA_CHECK *param, register MARIA_HA *info, param->testflag|=T_CALC_CHECKSUM; if (!param->using_global_keycache) - VOID(init_key_cache(maria_key_cache, param->key_cache_block_size, - param->use_buffers, 0, 0)); + VOID(init_pagecache(maria_pagecache, param->use_buffers, 0, 0, + param->pagecache_block_size)); - if (init_io_cache(¶m->read_cache,info->dfile, + if (init_io_cache(¶m->read_cache, info->dfile.file, (uint) param->read_buffer_length, READ_CACHE,share->pack.header_length,1,MYF(MY_WME))) { @@ -1959,8 +1962,8 @@ int maria_repair(HA_CHECK *param, register MARIA_HA *info, goto err; } if (new_header_length && - maria_filecopy(param,new_file,info->dfile,0L,new_header_length, - "datafile-header")) + maria_filecopy(param, new_file, info->dfile.file, 0L, + new_header_length, "datafile-header")) goto err; info->s->state.dellink= HA_OFFSET_ERROR; info->rec_cache.file=new_file; @@ -1973,7 +1976,7 @@ int maria_repair(HA_CHECK *param, register MARIA_HA *info, sort_param.pos=sort_param.max_pos=share->pack.header_length; sort_param.filepos=new_header_length; param->read_cache.end_of_file=sort_info.filelength= - my_seek(info->dfile,0L,MY_SEEK_END,MYF(0)); + my_seek(info->dfile.file, 0L, MY_SEEK_END, MYF(0)); sort_info.dupp=0; sort_param.fix_datafile= (my_bool) (! rep_quick); sort_param.master=1; @@ -2049,7 +2052,7 @@ int maria_repair(HA_CHECK *param, register MARIA_HA *info, { VOID(fputs(" \r",stdout)); VOID(fflush(stdout)); } - if (my_chsize(share->kfile,info->state->key_file_length,0,MYF(0))) + if (my_chsize(share->kfile.file, info->state->key_file_length, 0, MYF(0))) { _ma_check_print_warning(param, "Can't change size of indexfile, error: %d", @@ -2079,8 +2082,8 @@ int maria_repair(HA_CHECK *param, register MARIA_HA *info, if (!rep_quick) { - my_close(info->dfile,MYF(0)); - info->dfile=new_file; + my_close(info->dfile.file, MYF(0)); + info->dfile.file= new_file; info->state->data_file_length=sort_param.filepos; share->state.version=(ulong) time((time_t*) 0); /* Force reopen */ } @@ -2113,7 +2116,7 @@ err: if (new_file >= 0) { my_close(new_file,MYF(0)); - info->dfile=new_file= -1; + info->dfile.file= new_file= -1; if (maria_change_to_newfile(share->data_file_name,MARIA_NAME_DEXT, DATA_TMP_EXT, (param->testflag & T_BACKUP_DATA ? MYF(MY_REDEL_MAKE_BACKUP): MYF(0))) || @@ -2140,7 +2143,7 @@ err: VOID(end_io_cache(¶m->read_cache)); info->opt_flag&= ~(READ_CACHE_USED | WRITE_CACHE_USED); VOID(end_io_cache(&info->rec_cache)); - got_error|=_ma_flush_blocks(param, share->key_cache, share->kfile); + got_error|=_ma_flush_blocks(param, share->pagecache, &share->kfile); if (!got_error && (param->testflag & T_UNPACK)) restore_data_file_type(share); share->state.changed|= (STATE_NOT_OPTIMIZED_KEYS | STATE_NOT_SORTED_PAGES | @@ -2283,15 +2286,16 @@ void maria_lock_memory(HA_CHECK *param __attribute__((unused))) /* Flush all changed blocks to disk */ -int _ma_flush_blocks(HA_CHECK *param, KEY_CACHE *key_cache, File file) +int _ma_flush_blocks(HA_CHECK *param, PAGECACHE *pagecache, + PAGECACHE_FILE *file) { - if (flush_key_blocks(key_cache, file, FLUSH_RELEASE)) + if (flush_pagecache_blocks(pagecache, file, FLUSH_RELEASE)) { _ma_check_print_error(param,"%d when trying to write bufferts",my_errno); return(1); } if (!param->using_global_keycache) - end_key_cache(key_cache,1); + end_pagecache(pagecache,1); return 0; } /* _ma_flush_blocks */ @@ -2323,7 +2327,7 @@ int maria_sort_index(HA_CHECK *param, register MARIA_HA *info, my_string name) param->temp_filename); DBUG_RETURN(-1); } - if (maria_filecopy(param, new_file,share->kfile,0L, + if (maria_filecopy(param, new_file, share->kfile.file, 0L, (ulong) share->base.keystart, "headerblock")) goto err; @@ -2346,7 +2350,8 @@ int maria_sort_index(HA_CHECK *param, register MARIA_HA *info, my_string name) } /* Flush key cache for this file if we are calling this outside maria_chk */ - flush_key_blocks(share->key_cache,share->kfile, FLUSH_IGNORE_CHANGED); + flush_pagecache_blocks(share->pagecache, &share->kfile, + FLUSH_IGNORE_CHANGED); share->state.version=(ulong) time((time_t*) 0); old_state= share->state; /* save state if not stored */ @@ -2357,8 +2362,8 @@ int maria_sort_index(HA_CHECK *param, register MARIA_HA *info, my_string name) /* Put same locks as old file */ share->r_locks= share->w_locks= share->tot_locks= 0; (void) _ma_writeinfo(info,WRITEINFO_UPDATE_KEYFILE); - VOID(my_close(share->kfile,MYF(MY_WME))); - share->kfile = -1; + VOID(my_close(share->kfile.file, MYF(MY_WME))); + share->kfile.file = -1; VOID(my_close(new_file,MYF(MY_WME))); if (maria_change_to_newfile(share->index_file_name, MARIA_NAME_IEXT, INDEX_TMP_EXT, MYF(0)) || @@ -2598,18 +2603,18 @@ int maria_repair_by_sort(HA_CHECK *param, register MARIA_HA *info, alloc_key_blocks(param, (uint) param->sort_key_blocks, share->base.max_key_block_length)) - || init_io_cache(¶m->read_cache,info->dfile, + || init_io_cache(¶m->read_cache, info->dfile.file, (uint) param->read_buffer_length, READ_CACHE,share->pack.header_length,1,MYF(MY_WME)) || (! rep_quick && - init_io_cache(&info->rec_cache,info->dfile, + init_io_cache(&info->rec_cache, info->dfile.file, (uint) param->write_buffer_length, WRITE_CACHE,new_header_length,1, MYF(MY_WME | MY_WAIT_IF_FULL) & param->myf_rw))) goto err; sort_info.key_block_end=sort_info.key_block+param->sort_key_blocks; info->opt_flag|=WRITE_CACHE_USED; - info->rec_cache.file=info->dfile; /* for sort_delete_record */ + info->rec_cache.file= info->dfile.file; /* for sort_delete_record */ if (!(sort_param.record=(byte*) my_malloc((uint) share->base.pack_reclength, MYF(0))) || @@ -2633,8 +2638,8 @@ int maria_repair_by_sort(HA_CHECK *param, register MARIA_HA *info, goto err; } if (new_header_length && - maria_filecopy(param, new_file,info->dfile,0L,new_header_length, - "datafile-header")) + maria_filecopy(param, new_file, info->dfile.file, 0L, + new_header_length, "datafile-header")) goto err; if (param->testflag & T_UNPACK) restore_data_file_type(share); @@ -2649,7 +2654,8 @@ int maria_repair_by_sort(HA_CHECK *param, register MARIA_HA *info, Flush key cache for this file if we are calling this outside maria_chk */ - flush_key_blocks(share->key_cache,share->kfile, FLUSH_IGNORE_CHANGED); + flush_pagecache_blocks(share->pagecache, &share->kfile, + FLUSH_IGNORE_CHANGED); /* Clear the pointers to the given rows */ for (i=0 ; i < share->base.keys ; i++) share->state.key_root[i]= HA_OFFSET_ERROR; @@ -2658,7 +2664,8 @@ int maria_repair_by_sort(HA_CHECK *param, register MARIA_HA *info, } else { - if (flush_key_blocks(share->key_cache,share->kfile, FLUSH_FORCE_WRITE)) + if (flush_pagecache_blocks(share->pagecache, &share->kfile, + FLUSH_FORCE_WRITE)) goto err; key_map= ~key_map; /* Create the missing keys */ } @@ -2812,8 +2819,8 @@ int maria_repair_by_sort(HA_CHECK *param, register MARIA_HA *info, sort_param.filepos; /* Only whole records */ share->state.version=(ulong) time((time_t*) 0); - my_close(info->dfile,MYF(0)); - info->dfile=new_file; + my_close(info->dfile.file, MYF(0)); + info->dfile.file= new_file; share->data_file_type=sort_info.new_data_file_type; share->pack.header_length=(ulong) new_header_length; sort_param.fix_datafile=0; @@ -2821,7 +2828,7 @@ int maria_repair_by_sort(HA_CHECK *param, register MARIA_HA *info, else info->state->data_file_length=sort_param.max_pos; - param->read_cache.file=info->dfile; /* re-init read cache */ + param->read_cache.file= info->dfile.file; /* re-init read cache */ reinit_io_cache(¶m->read_cache,READ_CACHE,share->pack.header_length, 1,1); } @@ -2852,7 +2859,7 @@ int maria_repair_by_sort(HA_CHECK *param, register MARIA_HA *info, skr=share->base.reloc*share->base.min_pack_length; #endif if (skr != sort_info.filelength) - if (my_chsize(info->dfile,skr,0,MYF(0))) + if (my_chsize(info->dfile.file, skr, 0, MYF(0))) _ma_check_print_warning(param, "Can't change size of datafile, error: %d", my_errno); @@ -2860,7 +2867,7 @@ int maria_repair_by_sort(HA_CHECK *param, register MARIA_HA *info, if (param->testflag & T_CALC_CHECKSUM) info->state->checksum=param->glob_crc; - if (my_chsize(share->kfile,info->state->key_file_length,0,MYF(0))) + if (my_chsize(share->kfile.file, info->state->key_file_length, 0, MYF(0))) _ma_check_print_warning(param, "Can't change size of indexfile, error: %d", my_errno); @@ -2880,7 +2887,7 @@ int maria_repair_by_sort(HA_CHECK *param, register MARIA_HA *info, memcpy( &share->state.state, info->state, sizeof(*info->state)); err: - got_error|= _ma_flush_blocks(param, share->key_cache, share->kfile); + got_error|= _ma_flush_blocks(param, share->pagecache, &share->kfile); VOID(end_io_cache(&info->rec_cache)); if (!got_error) { @@ -2888,7 +2895,7 @@ err: if (new_file >= 0) { my_close(new_file,MYF(0)); - info->dfile=new_file= -1; + info->dfile.file= new_file= -1; if (maria_change_to_newfile(share->data_file_name,MARIA_NAME_DEXT, DATA_TMP_EXT, (param->testflag & T_BACKUP_DATA ? @@ -2905,8 +2912,8 @@ err: { VOID(my_close(new_file,MYF(0))); VOID(my_delete(param->temp_filename, MYF(MY_WME))); - if (info->dfile == new_file) - info->dfile= -1; + if (info->dfile.file == new_file) + info->dfile.file= -1; } maria_mark_crashed_on_repair(info); } @@ -3010,14 +3017,14 @@ int maria_repair_parallel(HA_CHECK *param, register MARIA_HA *info, /* Quick repair (not touching data file, rebuilding indexes): { - Read cache is (MI_CHECK *param)->read_cache using info->dfile. + Read cache is (MI_CHECK *param)->read_cache using info->dfile.file. } Non-quick repair (rebuilding data file and indexes): { Master thread: - Read cache is (MI_CHECK *param)->read_cache using info->dfile. + Read cache is (MI_CHECK *param)->read_cache using info->dfile.file. Write cache is (MI_INFO *info)->rec_cache using new_file. Slave threads: @@ -3044,11 +3051,11 @@ int maria_repair_parallel(HA_CHECK *param, register MARIA_HA *info, if (!(sort_info.key_block= alloc_key_blocks(param, (uint) param->sort_key_blocks, share->base.max_key_block_length)) || - init_io_cache(¶m->read_cache, info->dfile, + init_io_cache(¶m->read_cache, info->dfile.file, (uint) param->read_buffer_length, READ_CACHE, share->pack.header_length, 1, MYF(MY_WME)) || (!rep_quick && - (init_io_cache(&info->rec_cache, info->dfile, + (init_io_cache(&info->rec_cache, info->dfile.file, (uint) param->write_buffer_length, WRITE_CACHE, new_header_length, 1, MYF(MY_WME | MY_WAIT_IF_FULL) & param->myf_rw) || @@ -3059,7 +3066,7 @@ int maria_repair_parallel(HA_CHECK *param, register MARIA_HA *info, goto err; sort_info.key_block_end=sort_info.key_block+param->sort_key_blocks; info->opt_flag|=WRITE_CACHE_USED; - info->rec_cache.file=info->dfile; /* for sort_delete_record */ + info->rec_cache.file= info->dfile.file; /* for sort_delete_record */ if (!rep_quick) { @@ -3076,7 +3083,7 @@ int maria_repair_parallel(HA_CHECK *param, register MARIA_HA *info, goto err; } if (new_header_length && - maria_filecopy(param, new_file,info->dfile,0L,new_header_length, + maria_filecopy(param, new_file, info->dfile.file,0L,new_header_length, "datafile-header")) goto err; if (param->testflag & T_UNPACK) @@ -3092,7 +3099,8 @@ int maria_repair_parallel(HA_CHECK *param, register MARIA_HA *info, Flush key cache for this file if we are calling this outside maria_chk */ - flush_key_blocks(share->key_cache,share->kfile, FLUSH_IGNORE_CHANGED); + flush_pagecache_blocks(share->pagecache, &share->kfile, + FLUSH_IGNORE_CHANGED); /* Clear the pointers to the given rows */ for (i=0 ; i < share->base.keys ; i++) share->state.key_root[i]= HA_OFFSET_ERROR; @@ -3101,7 +3109,8 @@ int maria_repair_parallel(HA_CHECK *param, register MARIA_HA *info, } else { - if (flush_key_blocks(share->key_cache,share->kfile, FLUSH_FORCE_WRITE)) + if (flush_pagecache_blocks(share->pagecache, &share->kfile, + FLUSH_FORCE_WRITE)) goto err; key_map= ~key_map; /* Create the missing keys */ } @@ -3331,8 +3340,8 @@ int maria_repair_parallel(HA_CHECK *param, register MARIA_HA *info, Exchange the data file descriptor of the table, so that we use the new file from now on. */ - my_close(info->dfile,MYF(0)); - info->dfile=new_file; + my_close(info->dfile.file, MYF(0)); + info->dfile.file= new_file; share->data_file_type=sort_info.new_data_file_type; share->pack.header_length=(ulong) new_header_length; @@ -3360,7 +3369,7 @@ int maria_repair_parallel(HA_CHECK *param, register MARIA_HA *info, skr=share->base.reloc*share->base.min_pack_length; #endif if (skr != sort_info.filelength) - if (my_chsize(info->dfile,skr,0,MYF(0))) + if (my_chsize(info->dfile.file, skr, 0, MYF(0))) _ma_check_print_warning(param, "Can't change size of datafile, error: %d", my_errno); @@ -3368,7 +3377,7 @@ int maria_repair_parallel(HA_CHECK *param, register MARIA_HA *info, if (param->testflag & T_CALC_CHECKSUM) info->state->checksum=param->glob_crc; - if (my_chsize(share->kfile,info->state->key_file_length,0,MYF(0))) + if (my_chsize(share->kfile.file, info->state->key_file_length, 0, MYF(0))) _ma_check_print_warning(param, "Can't change size of indexfile, error: %d", my_errno); @@ -3387,7 +3396,7 @@ int maria_repair_parallel(HA_CHECK *param, register MARIA_HA *info, memcpy(&share->state.state, info->state, sizeof(*info->state)); err: - got_error|= _ma_flush_blocks(param, share->key_cache, share->kfile); + got_error|= _ma_flush_blocks(param, share->pagecache, &share->kfile); /* Destroy the write cache. The master thread did already detach from the share by remove_io_thread() or it was not yet started (if the @@ -3408,7 +3417,7 @@ err: if (new_file >= 0) { my_close(new_file,MYF(0)); - info->dfile=new_file= -1; + info->dfile.file= new_file= -1; if (maria_change_to_newfile(share->data_file_name,MARIA_NAME_DEXT, DATA_TMP_EXT, (param->testflag & T_BACKUP_DATA ? @@ -3425,8 +3434,8 @@ err: { VOID(my_close(new_file,MYF(0))); VOID(my_delete(param->temp_filename, MYF(MY_WME))); - if (info->dfile == new_file) - info->dfile= -1; + if (info->dfile.file == new_file) + info->dfile.file= -1; } maria_mark_crashed_on_repair(info); } @@ -4400,7 +4409,7 @@ static int sort_insert_key(MARIA_SORT_PARAM *sort_param, if (_ma_write_keypage(info, keyinfo, filepos, DFLT_INIT_HITS, anc_buff)) DBUG_RETURN(1); } - else if (my_pwrite(info->s->kfile,anc_buff, + else if (my_pwrite(info->s->kfile.file, anc_buff, (uint) keyinfo->block_length,filepos, param->myf_rw)) DBUG_RETURN(1); DBUG_DUMP("buff",anc_buff,maria_getint(anc_buff)); @@ -4440,8 +4449,8 @@ static int sort_delete_record(MARIA_SORT_PARAM *sort_param) DBUG_RETURN(1); } - old_file=info->dfile; - info->dfile=info->rec_cache.file; + old_file= info->dfile.file; + info->dfile.file= info->rec_cache.file; if (sort_info->current_key) { key= info->lastkey+info->s->base.max_key_length; @@ -4450,7 +4459,7 @@ static int sort_delete_record(MARIA_SORT_PARAM *sort_param) error != HA_ERR_RECORD_DELETED) { _ma_check_print_error(param,"Can't read record to be removed"); - info->dfile=old_file; + info->dfile.file= old_file; DBUG_RETURN(1); } @@ -4463,7 +4472,7 @@ static int sort_delete_record(MARIA_SORT_PARAM *sort_param) _ma_check_print_error(param, "Can't delete key %d from record to be removed", i+1); - info->dfile=old_file; + info->dfile.file= old_file; DBUG_RETURN(1); } } @@ -4471,7 +4480,7 @@ static int sort_delete_record(MARIA_SORT_PARAM *sort_param) param->glob_crc-=(*info->s->calc_checksum)(info, sort_param->record); } error=flush_io_cache(&info->rec_cache) || (*info->s->delete_record)(info); - info->dfile=old_file; /* restore actual value */ + info->dfile.file= old_file; /* restore actual value */ info->state->records--; DBUG_RETURN(error); } /* sort_delete_record */ @@ -4509,7 +4518,7 @@ int _ma_flush_pending_blocks(MARIA_SORT_PARAM *sort_param) DFLT_INIT_HITS, key_block->buff)) DBUG_RETURN(1); } - else if (my_pwrite(info->s->kfile,key_block->buff, + else if (my_pwrite(info->s->kfile.file, key_block->buff, (uint) keyinfo->block_length,filepos, myf_rw)) DBUG_RETURN(1); DBUG_DUMP("buff",key_block->buff,length); @@ -4550,9 +4559,9 @@ int maria_test_if_almost_full(MARIA_HA *info) { if (info->s->options & HA_OPTION_COMPRESS_RECORD) return 0; - return (my_seek(info->s->kfile,0L,MY_SEEK_END,MYF(0))/10*9 > + return (my_seek(info->s->kfile.file, 0L, MY_SEEK_END, MYF(0))/10*9 > (my_off_t) (info->s->base.max_key_file_length) || - my_seek(info->dfile,0L,MY_SEEK_END,MYF(0))/10*9 > + my_seek(info->dfile.file, 0L, MY_SEEK_END, MYF(0)) / 10 * 9 > (my_off_t) info->s->base.max_data_file_length); } @@ -4653,7 +4662,8 @@ int maria_recreate_table(HA_CHECK *param, MARIA_HA **org_info, char *filename) if (share.options & HA_OPTION_COMPRESS_RECORD) share.base.records=max_records=info.state->records; else if (share.base.min_pack_length) - max_records=(ha_rows) (my_seek(info.dfile,0L,MY_SEEK_END,MYF(0)) / + max_records=(ha_rows) (my_seek(info.dfile.file, 0L, MY_SEEK_END, + MYF(0)) / (ulong) share.base.min_pack_length); else max_records=0; @@ -4661,7 +4671,7 @@ int maria_recreate_table(HA_CHECK *param, MARIA_HA **org_info, char *filename) (param->testflag & T_UNPACK); share.options&= ~HA_OPTION_TEMP_COMPRESS_RECORD; - file_length=(ulonglong) my_seek(info.dfile,0L,MY_SEEK_END,MYF(0)); + file_length=(ulonglong) my_seek(info.dfile.file, 0L, MY_SEEK_END, MYF(0)); tmp_length= file_length+file_length/10; set_if_bigger(file_length,param->max_data_file_length); set_if_bigger(file_length,tmp_length); @@ -4804,7 +4814,7 @@ int maria_update_state_info(HA_CHECK *param, MARIA_HA *info,uint update) */ if (info->lock_type == F_WRLCK) share->state.state= *info->state; - if (_ma_state_info_write(share->kfile,&share->state,1+2)) + if (_ma_state_info_write(share->kfile.file, &share->state, 1 + 2)) goto err; share->changed=0; } diff --git a/storage/maria/ma_close.c b/storage/maria/ma_close.c index 2a874079961..05259218e6d 100644 --- a/storage/maria/ma_close.c +++ b/storage/maria/ma_close.c @@ -36,7 +36,7 @@ int maria_close(register MARIA_HA *info) if (info->lock_type == F_EXTRA_LCK) info->lock_type=F_UNLCK; /* HA_EXTRA_NO_USER_CHANGE */ - if (share->reopen == 1 && share->kfile >= 0) + if (share->reopen == 1 && share->kfile.file >= 0) _ma_decrement_open_count(info); if (info->lock_type != F_UNLCK) @@ -73,16 +73,17 @@ int maria_close(register MARIA_HA *info) (share->end)(info); if (info->s->data_file_type == BLOCK_RECORD) - info->dfile= -1; /* Closed in ma_end_once_block_row */ + info->dfile.file= -1; /* Closed in ma_end_once_block_row */ if (flag) { - if (share->kfile >= 0) + if (share->kfile.file >= 0) { if ((*share->once_end)(share)) error= my_errno; - if (flush_key_blocks(share->key_cache, share->kfile, - share->temporary ? FLUSH_IGNORE_CHANGED : - FLUSH_RELEASE)) + if (flush_pagecache_blocks(share->pagecache, &share->kfile, + (share->temporary ? + FLUSH_IGNORE_CHANGED : + FLUSH_RELEASE))) error= my_errno; /* @@ -92,8 +93,8 @@ int maria_close(register MARIA_HA *info) may be using the file at this point */ if (share->mode != O_RDONLY && maria_is_crashed(info)) - _ma_state_info_write(share->kfile, &share->state, 1); - if (my_close(share->kfile, MYF(0))) + _ma_state_info_write(share->kfile.file, &share->state, 1); + if (my_close(share->kfile.file, MYF(0))) error= my_errno; } #ifdef HAVE_MMAP @@ -120,7 +121,7 @@ int maria_close(register MARIA_HA *info) my_free((gptr)info->ftparser_param, MYF(0)); info->ftparser_param= 0; } - if (info->dfile >= 0 && my_close(info->dfile,MYF(0))) + if (info->dfile.file >= 0 && my_close(info->dfile.file, MYF(0))) error = my_errno; my_free((gptr) info,MYF(0)); diff --git a/storage/maria/ma_delete_all.c b/storage/maria/ma_delete_all.c index 616147c1067..d12e58c49c9 100644 --- a/storage/maria/ma_delete_all.c +++ b/storage/maria/ma_delete_all.c @@ -52,7 +52,8 @@ int maria_delete_all_rows(MARIA_HA *info) If we are using delayed keys or if the user has done changes to the tables since it was locked then there may be key blocks in the key cache */ - flush_key_blocks(share->key_cache, share->kfile, FLUSH_IGNORE_CHANGED); + flush_pagecache_blocks(share->pagecache, &share->kfile, + FLUSH_IGNORE_CHANGED); /* RECOVERYTODO Log the two chsize and header modifications and force the log. So that if crash between the two chsize, we finish the work at @@ -62,8 +63,8 @@ int maria_delete_all_rows(MARIA_HA *info) should be applied only if t1 exists and its ZeroDirtyPagesLSN is smaller than the records'. See more comments below. */ - if (my_chsize(info->dfile, 0, 0, MYF(MY_WME)) || - my_chsize(share->kfile, share->base.keystart, 0, MYF(MY_WME)) ) + if (my_chsize(info->dfile.file, 0, 0, MYF(MY_WME)) || + my_chsize(share->kfile.file, share->base.keystart, 0, MYF(MY_WME)) ) goto err; /* RECOVERYTODO Consider updating ZeroDirtyPagesLSN here. It is diff --git a/storage/maria/ma_dynrec.c b/storage/maria/ma_dynrec.c index c3d0bf1fb0a..aeedd4519c1 100644 --- a/storage/maria/ma_dynrec.c +++ b/storage/maria/ma_dynrec.c @@ -74,7 +74,7 @@ my_bool _ma_dynmap_file(MARIA_HA *info, my_off_t size) info->s->mode==O_RDONLY ? PROT_READ : PROT_READ | PROT_WRITE, MAP_SHARED | MAP_NORESERVE, - info->dfile, 0L); + info->dfile.file, 0L); if (info->s->file_map == (byte*) MAP_FAILED) { info->s->file_map= NULL; @@ -128,7 +128,7 @@ void _ma_remap_file(MARIA_HA *info, my_off_t size) uint _ma_mmap_pread(MARIA_HA *info, byte *Buffer, uint Count, my_off_t offset, myf MyFlags) { - DBUG_PRINT("info", ("maria_read with mmap %d\n", info->dfile)); + DBUG_PRINT("info", ("maria_read with mmap %d\n", info->dfile.file)); if (info->s->concurrent_insert) rw_rdlock(&info->s->mmap_lock); @@ -150,7 +150,7 @@ uint _ma_mmap_pread(MARIA_HA *info, byte *Buffer, { if (info->s->concurrent_insert) rw_unlock(&info->s->mmap_lock); - return my_pread(info->dfile, Buffer, Count, offset, MyFlags); + return my_pread(info->dfile.file, Buffer, Count, offset, MyFlags); } } @@ -160,7 +160,7 @@ uint _ma_mmap_pread(MARIA_HA *info, byte *Buffer, uint _ma_nommap_pread(MARIA_HA *info, byte *Buffer, uint Count, my_off_t offset, myf MyFlags) { - return my_pread(info->dfile, Buffer, Count, offset, MyFlags); + return my_pread(info->dfile.file, Buffer, Count, offset, MyFlags); } @@ -183,7 +183,7 @@ uint _ma_nommap_pread(MARIA_HA *info, byte *Buffer, uint _ma_mmap_pwrite(MARIA_HA *info, byte *Buffer, uint Count, my_off_t offset, myf MyFlags) { - DBUG_PRINT("info", ("maria_write with mmap %d\n", info->dfile)); + DBUG_PRINT("info", ("maria_write with mmap %d\n", info->dfile.file)); if (info->s->concurrent_insert) rw_rdlock(&info->s->mmap_lock); @@ -206,7 +206,7 @@ uint _ma_mmap_pwrite(MARIA_HA *info, byte *Buffer, info->s->nonmmaped_inserts++; if (info->s->concurrent_insert) rw_unlock(&info->s->mmap_lock); - return my_pwrite(info->dfile, Buffer, Count, offset, MyFlags); + return my_pwrite(info->dfile.file, Buffer, Count, offset, MyFlags); } } @@ -217,7 +217,7 @@ uint _ma_mmap_pwrite(MARIA_HA *info, byte *Buffer, uint _ma_nommap_pwrite(MARIA_HA *info, byte *Buffer, uint Count, my_off_t offset, myf MyFlags) { - return my_pwrite(info->dfile, Buffer, Count, offset, MyFlags); + return my_pwrite(info->dfile.file, Buffer, Count, offset, MyFlags); } @@ -354,7 +354,8 @@ static int _ma_find_writepos(MARIA_HA *info, *filepos=info->s->state.dellink; block_info.second_read=0; info->rec_cache.seek_not_done=1; - if (!(_ma_get_block_info(&block_info,info->dfile,info->s->state.dellink) & + if (!(_ma_get_block_info(&block_info, info->dfile.file, + info->s->state.dellink) & BLOCK_DELETED)) { DBUG_PRINT("error",("Delete link crashed")); @@ -413,7 +414,7 @@ static bool unlink_deleted_block(MARIA_HA *info, MARIA_BLOCK_INFO *block_info) MARIA_BLOCK_INFO tmp; tmp.second_read=0; /* Unlink block from the previous block */ - if (!(_ma_get_block_info(&tmp,info->dfile,block_info->prev_filepos) + if (!(_ma_get_block_info(&tmp, info->dfile.file, block_info->prev_filepos) & BLOCK_DELETED)) DBUG_RETURN(1); /* Something is wrong */ mi_sizestore(tmp.header+4,block_info->next_filepos); @@ -423,7 +424,8 @@ static bool unlink_deleted_block(MARIA_HA *info, MARIA_BLOCK_INFO *block_info) /* Unlink block from next block */ if (block_info->next_filepos != HA_OFFSET_ERROR) { - if (!(_ma_get_block_info(&tmp,info->dfile,block_info->next_filepos) + if (!(_ma_get_block_info(&tmp, info->dfile.file, + block_info->next_filepos) & BLOCK_DELETED)) DBUG_RETURN(1); /* Something is wrong */ mi_sizestore(tmp.header+12,block_info->prev_filepos); @@ -474,7 +476,7 @@ static my_bool update_backward_delete_link(MARIA_HA *info, if (delete_block != HA_OFFSET_ERROR) { block_info.second_read=0; - if (_ma_get_block_info(&block_info,info->dfile,delete_block) + if (_ma_get_block_info(&block_info, info->dfile.file, delete_block) & BLOCK_DELETED) { char buff[8]; @@ -510,7 +512,7 @@ static my_bool delete_dynamic_record(MARIA_HA *info, MARIA_RECORD_POS filepos, do { /* Remove block at 'filepos' */ - if ((b_type= _ma_get_block_info(&block_info,info->dfile,filepos)) + if ((b_type= _ma_get_block_info(&block_info, info->dfile.file, filepos)) & (BLOCK_DELETED | BLOCK_ERROR | BLOCK_SYNC_ERROR | BLOCK_FATAL_ERROR) || (length=(uint) (block_info.filepos-filepos) +block_info.block_len) < @@ -522,7 +524,7 @@ static my_bool delete_dynamic_record(MARIA_HA *info, MARIA_RECORD_POS filepos, /* Check if next block is a delete block */ del_block.second_read=0; remove_next_block=0; - if (_ma_get_block_info(&del_block,info->dfile,filepos+length) & + if (_ma_get_block_info(&del_block, info->dfile.file, filepos + length) & BLOCK_DELETED && del_block.block_len+length < MARIA_DYN_MAX_BLOCK_LENGTH) { @@ -682,7 +684,7 @@ int _ma_write_part_record(MARIA_HA *info, if (next_block < info->state->data_file_length && info->s->state.dellink != HA_OFFSET_ERROR) { - if ((_ma_get_block_info(&del_block,info->dfile,next_block) + if ((_ma_get_block_info(&del_block, info->dfile.file, next_block) & BLOCK_DELETED) && res_length + del_block.block_len < MARIA_DYN_MAX_BLOCK_LENGTH) { @@ -763,7 +765,7 @@ static my_bool update_dynamic_record(MARIA_HA *info, MARIA_RECORD_POS filepos, if (filepos != info->s->state.dellink) { block_info.next_filepos= HA_OFFSET_ERROR; - if ((error= _ma_get_block_info(&block_info,info->dfile,filepos)) + if ((error= _ma_get_block_info(&block_info, info->dfile.file, filepos)) & (BLOCK_DELETED | BLOCK_ERROR | BLOCK_SYNC_ERROR | BLOCK_FATAL_ERROR)) { @@ -804,7 +806,7 @@ static my_bool update_dynamic_record(MARIA_HA *info, MARIA_RECORD_POS filepos, MARIA_BLOCK_INFO del_block; del_block.second_read=0; - if (_ma_get_block_info(&del_block,info->dfile, + if (_ma_get_block_info(&del_block, info->dfile.file, block_info.filepos + block_info.block_len) & BLOCK_DELETED) { @@ -1370,7 +1372,7 @@ int _ma_read_dynamic_record(MARIA_HA *info, byte *buf, { LINT_INIT(to); LINT_INIT(left_length); - file=info->dfile; + file= info->dfile.file; block_of_record= 0; /* First block of record is numbered as zero. */ block_info.second_read= 0; do @@ -1534,7 +1536,7 @@ my_bool _ma_cmp_dynamic_record(register MARIA_HA *info, block_info.next_filepos=filepos; while (reclength > 0) { - if ((b_type= _ma_get_block_info(&block_info,info->dfile, + if ((b_type= _ma_get_block_info(&block_info, info->dfile.file, block_info.next_filepos)) & (BLOCK_DELETED | BLOCK_ERROR | BLOCK_SYNC_ERROR | BLOCK_FATAL_ERROR)) @@ -1561,7 +1563,7 @@ my_bool _ma_cmp_dynamic_record(register MARIA_HA *info, if (!reclength && info->s->calc_checksum) cmp_length--; /* 'record' may not contain checksum */ - if (_ma_cmp_buffer(info->dfile,record,block_info.filepos, + if (_ma_cmp_buffer(info->dfile.file, record, block_info.filepos, cmp_length)) { my_errno=HA_ERR_RECORD_CHANGED; @@ -1680,7 +1682,7 @@ int _ma_read_rnd_dynamic_record(MARIA_HA *info, { /* Check if changed */ info_read=1; info->rec_cache.seek_not_done=1; - if (_ma_state_info_read_dsk(share->kfile,&share->state,1)) + if (_ma_state_info_read_dsk(share->kfile.file, &share->state, 1)) goto panic; } if (filepos >= info->state->data_file_length) @@ -1705,7 +1707,7 @@ int _ma_read_rnd_dynamic_record(MARIA_HA *info, flush_io_cache(&info->rec_cache)) DBUG_RETURN(my_errno); info->rec_cache.seek_not_done=1; - b_type= _ma_get_block_info(&block_info,info->dfile,filepos); + b_type= _ma_get_block_info(&block_info, info->dfile.file, filepos); } if (b_type & (BLOCK_DELETED | BLOCK_ERROR | BLOCK_SYNC_ERROR | @@ -1779,8 +1781,9 @@ int _ma_read_rnd_dynamic_record(MARIA_HA *info, block_info.filepos + block_info.data_len && flush_io_cache(&info->rec_cache)) goto err; - /* VOID(my_seek(info->dfile,filepos,MY_SEEK_SET,MYF(0))); */ - if (my_read(info->dfile,(byte*) to,block_info.data_len,MYF(MY_NABP))) + /* VOID(my_seek(info->dfile.file, filepos, MY_SEEK_SET, MYF(0))); */ + if (my_read(info->dfile.file, (byte*)to, block_info.data_len, + MYF(MY_NABP))) { if (my_errno == -1) my_errno= HA_ERR_WRONG_IN_RECORD; /* Unexpected end of file */ diff --git a/storage/maria/ma_extra.c b/storage/maria/ma_extra.c index 90e79362442..3c35d7d20fc 100644 --- a/storage/maria/ma_extra.c +++ b/storage/maria/ma_extra.c @@ -101,7 +101,7 @@ int maria_extra(MARIA_HA *info, enum ha_extra_function function, { cache_size= (extra_arg ? *(ulong*) extra_arg : my_default_record_cache_size); - if (!(init_io_cache(&info->rec_cache,info->dfile, + if (!(init_io_cache(&info->rec_cache, info->dfile.file, (uint) min(info->state->data_file_length+1, cache_size), READ_CACHE,0L,(pbool) (info->lock_type != F_UNLCK), @@ -137,7 +137,7 @@ int maria_extra(MARIA_HA *info, enum ha_extra_function function, if (!(info->opt_flag & (READ_CACHE_USED | WRITE_CACHE_USED | OPT_NO_ROWS)) && !share->state.header.uniques) - if (!(init_io_cache(&info->rec_cache,info->dfile, cache_size, + if (!(init_io_cache(&info->rec_cache, info->dfile.file, cache_size, WRITE_CACHE,info->state->data_file_length, (pbool) (info->lock_type != F_UNLCK), MYF(share->write_flag & MY_WAIT_IF_FULL)))) @@ -250,7 +250,7 @@ int maria_extra(MARIA_HA *info, enum ha_extra_function function, } } share->state.state= *info->state; - error=_ma_state_info_write(share->kfile,&share->state,1 | 2); + error=_ma_state_info_write(share->kfile.file, &share->state, (1 | 2)); } break; case HA_EXTRA_FORCE_REOPEN: @@ -264,8 +264,8 @@ int maria_extra(MARIA_HA *info, enum ha_extra_function function, #ifdef __WIN__ /* Close the isam and data files as Win32 can't drop an open table */ pthread_mutex_lock(&share->intern_lock); - if (flush_key_blocks(share->key_cache, share->kfile, - (function == HA_EXTRA_FORCE_REOPEN ? + if (flush_pagecache_blocks(share->pagecache, &share->kfile, + (function == HA_EXTRA_FORCE_REOPEN ? FLUSH_RELEASE : FLUSH_IGNORE_CHANGED))) { error=my_errno; @@ -285,9 +285,9 @@ int maria_extra(MARIA_HA *info, enum ha_extra_function function, error=my_errno; info->lock_type = F_UNLCK; } - if (share->kfile >= 0) + if (share->kfile.file >= 0) _ma_decrement_open_count(info); - if (share->kfile >= 0 && my_close(share->kfile,MYF(0))) + if (share->kfile.file >= 0 && my_close(share->kfile,MYF(0))) error=my_errno; { LIST *list_element ; @@ -298,20 +298,21 @@ int maria_extra(MARIA_HA *info, enum ha_extra_function function, MARIA_HA *tmpinfo=(MARIA_HA*) list_element->data; if (tmpinfo->s == info->s) { - if (tmpinfo->dfile >= 0 && my_close(tmpinfo->dfile,MYF(0))) + if (tmpinfo->dfile.file >= 0 && + my_close(tmpinfo->dfile.file, MYF(0))) error = my_errno; - tmpinfo->dfile= -1; + tmpinfo->dfile.file= -1; } } } - share->kfile= -1; /* Files aren't open anymore */ + share->kfile.file= -1; /* Files aren't open anymore */ pthread_mutex_unlock(&share->intern_lock); #endif pthread_mutex_unlock(&THR_LOCK_maria); break; case HA_EXTRA_FLUSH: if (!share->temporary) - flush_key_blocks(share->key_cache, share->kfile, FLUSH_KEEP); + flush_pagecache_blocks(share->pagecache, &share->kfile, FLUSH_KEEP); #ifdef HAVE_PWRITE _ma_decrement_open_count(info); #endif @@ -453,6 +454,6 @@ int maria_reset(MARIA_HA *info) int _ma_sync_table_files(const MARIA_HA *info) { - return (my_sync(info->dfile, MYF(0)) || - my_sync(info->s->kfile, MYF(0))); + return (my_sync(info->dfile.file, MYF(0)) || + my_sync(info->s->kfile.file, MYF(0))); } diff --git a/storage/maria/ma_info.c b/storage/maria/ma_info.c index 397cd2465d4..e76692960c6 100644 --- a/storage/maria/ma_info.c +++ b/storage/maria/ma_info.c @@ -72,7 +72,7 @@ int maria_status(MARIA_HA *info, register MARIA_INFO *x, uint flag) x->reclength = share->base.reclength; x->max_data_file_length=share->base.max_data_file_length; x->max_index_file_length=info->s->base.max_key_file_length; - x->filenr = info->dfile; + x->filenr = info->dfile.file; x->options = share->options; x->create_time=share->state.create_time; x->reflength= maria_get_pointer_length(share->base.max_data_file_length, @@ -86,7 +86,7 @@ int maria_status(MARIA_HA *info, register MARIA_INFO *x, uint flag) x->data_file_name = share->data_file_name; x->index_file_name = share->index_file_name; } - if ((flag & HA_STATUS_TIME) && !my_fstat(info->dfile,&state,MYF(0))) + if ((flag & HA_STATUS_TIME) && !my_fstat(info->dfile.file, &state, MYF(0))) x->update_time=state.st_mtime; else x->update_time=0; diff --git a/storage/maria/ma_keycache.c b/storage/maria/ma_keycache.c index 64725baae86..a9df52eadf9 100644 --- a/storage/maria/ma_keycache.c +++ b/storage/maria/ma_keycache.c @@ -24,10 +24,10 @@ Assign pages of the index file for a table to a key cache SYNOPSIS - maria_assign_to_key_cache() + maria_assign_to_pagecache() info open table key_map map of indexes to assign to the key cache - key_cache_ptr pointer to the key cache handle + pagecache_ptr pointer to the key cache handle assign_lock Mutex to lock during assignment PREREQUESTS @@ -47,22 +47,22 @@ # Error code */ -int maria_assign_to_key_cache(MARIA_HA *info, - ulonglong key_map __attribute__((unused)), - KEY_CACHE *key_cache) +int maria_assign_to_pagecache(MARIA_HA *info, + ulonglong key_map __attribute__((unused)), + PAGECACHE *pagecache) { int error= 0; MARIA_SHARE* share= info->s; - DBUG_ENTER("maria_assign_to_key_cache"); + DBUG_ENTER("maria_assign_to_pagecache"); DBUG_PRINT("enter", - ("old_key_cache_handle: 0x%lx new_key_cache_handle: 0x%lx", - (long) share->key_cache, (long) key_cache)); + ("old_pagecache_handle: 0x%lx new_pagecache_handle: 0x%lx", + (long) share->pagecache, (long) pagecache)); /* Skip operation if we didn't change key cache. This can happen if we call this for all open instances of the same table */ - if (share->key_cache == key_cache) + if (share->pagecache == pagecache) DBUG_RETURN(0); /* @@ -77,7 +77,7 @@ int maria_assign_to_key_cache(MARIA_HA *info, in the old key cache. */ - if (flush_key_blocks(share->key_cache, share->kfile, FLUSH_RELEASE)) + if (flush_pagecache_blocks(share->pagecache, &share->kfile, FLUSH_RELEASE)) { error= my_errno; maria_print_error(info->s, HA_ERR_CRASHED); @@ -92,10 +92,10 @@ int maria_assign_to_key_cache(MARIA_HA *info, (This can never fail as there is never any not written data in the new key cache) */ - (void) flush_key_blocks(key_cache, share->kfile, FLUSH_RELEASE); + (void) flush_pagecache_blocks(pagecache, &share->kfile, FLUSH_RELEASE); /* - ensure that setting the key cache and changing the multi_key_cache + ensure that setting the key cache and changing the multi_pagecache is done atomicly */ pthread_mutex_lock(&share->intern_lock); @@ -103,11 +103,11 @@ int maria_assign_to_key_cache(MARIA_HA *info, Tell all threads to use the new key cache This should be seen at the lastes for the next call to an maria function. */ - share->key_cache= key_cache; + share->pagecache= pagecache; /* store the key cache in the global hash structure for future opens */ - if (multi_key_cache_set(share->unique_file_name, share->unique_name_length, - share->key_cache)) + if (multi_pagecache_set(share->unique_file_name, share->unique_name_length, + share->pagecache)) error= my_errno; pthread_mutex_unlock(&share->intern_lock); DBUG_RETURN(error); @@ -118,16 +118,16 @@ int maria_assign_to_key_cache(MARIA_HA *info, Change all MARIA entries that uses one key cache to another key cache SYNOPSIS - maria_change_key_cache() - old_key_cache Old key cache - new_key_cache New key cache + maria_change_pagecache() + old_pagecache Old key cache + new_pagecache New key cache NOTES This is used when we delete one key cache. To handle the case where some other threads tries to open an MARIA table associated with the to-be-deleted key cache while this operation - is running, we have to call 'multi_key_cache_change()' from this + is running, we have to call 'multi_pagecache_change()' from this function while we have a lock on the MARIA table list structure. This is safe as long as it's only MARIA that is using this specific @@ -135,11 +135,11 @@ int maria_assign_to_key_cache(MARIA_HA *info, */ -void maria_change_key_cache(KEY_CACHE *old_key_cache, - KEY_CACHE *new_key_cache) +void maria_change_pagecache(PAGECACHE *old_pagecache, + PAGECACHE *new_pagecache) { LIST *pos; - DBUG_ENTER("maria_change_key_cache"); + DBUG_ENTER("maria_change_pagecache"); /* Lock list to ensure that no one can close the table while we manipulate it @@ -149,8 +149,8 @@ void maria_change_key_cache(KEY_CACHE *old_key_cache, { MARIA_HA *info= (MARIA_HA*) pos->data; MARIA_SHARE *share= info->s; - if (share->key_cache == old_key_cache) - maria_assign_to_key_cache(info, (ulonglong) ~0, new_key_cache); + if (share->pagecache == old_pagecache) + maria_assign_to_pagecache(info, (ulonglong) ~0, new_pagecache); } /* @@ -158,7 +158,7 @@ void maria_change_key_cache(KEY_CACHE *old_key_cache, MARIA list structure to ensure that another thread is not trying to open a new table that will be associted with the old key cache */ - multi_key_cache_change(old_key_cache, new_key_cache); + multi_pagecache_change(old_pagecache, new_pagecache); pthread_mutex_unlock(&THR_LOCK_maria); DBUG_VOID_RETURN; } diff --git a/storage/maria/ma_locking.c b/storage/maria/ma_locking.c index 6a0bbe82dcb..d59eca7d36b 100644 --- a/storage/maria/ma_locking.c +++ b/storage/maria/ma_locking.c @@ -50,7 +50,7 @@ int maria_lock_database(MARIA_HA *info, int lock_type) error=0; pthread_mutex_lock(&share->intern_lock); - if (share->kfile >= 0) /* May only be false on windows */ + if (share->kfile.file >= 0) /* May only be false on windows */ { switch (lock_type) { case F_UNLCK: @@ -62,9 +62,9 @@ int maria_lock_database(MARIA_HA *info, int lock_type) --share->tot_locks; if (info->lock_type == F_WRLCK && !share->w_locks) { - if (!share->delay_key_write && flush_key_blocks(share->key_cache, - share->kfile, - FLUSH_KEEP)) + if (!share->delay_key_write && + flush_pagecache_blocks(share->pagecache, &share->kfile, + FLUSH_KEEP)) { error= my_errno; maria_print_error(info->s, HA_ERR_CRASHED); @@ -72,7 +72,7 @@ int maria_lock_database(MARIA_HA *info, int lock_type) maria_mark_crashed(info); } if (share->data_file_type == BLOCK_RECORD && - flush_key_blocks(share->key_cache, info->dfile, FLUSH_KEEP)) + flush_pagecache_blocks(share->pagecache, &info->dfile, FLUSH_KEEP)) { error= my_errno; maria_print_error(info->s, HA_ERR_CRASHED); @@ -111,7 +111,7 @@ int maria_lock_database(MARIA_HA *info, int lock_type) share->state.process= share->last_process=share->this_process; share->state.unique= info->last_unique= info->this_unique; share->state.update_count= info->last_loop= ++info->this_loop; - if (_ma_state_info_write(share->kfile, &share->state, 1)) + if (_ma_state_info_write(share->kfile.file, &share->state, 1)) error=my_errno; share->changed=0; if (maria_flush) @@ -147,7 +147,7 @@ int maria_lock_database(MARIA_HA *info, int lock_type) } if (!share->r_locks && !share->w_locks) { - if (_ma_state_info_read_dsk(share->kfile, &share->state, 1)) + if (_ma_state_info_read_dsk(share->kfile.file, &share->state, 1)) { error=my_errno; break; @@ -175,7 +175,7 @@ int maria_lock_database(MARIA_HA *info, int lock_type) { if (!share->r_locks) { - if (_ma_state_info_read_dsk(share->kfile, &share->state, 1)) + if (_ma_state_info_read_dsk(share->kfile.file, &share->state, 1)) { error=my_errno; break; @@ -203,7 +203,7 @@ int maria_lock_database(MARIA_HA *info, int lock_type) a crash on windows if the table is renamed and later on referenced by the merge table. */ - if( info->owned_by_merge && (info->s)->kfile < 0 ) + if( info->owned_by_merge && (info->s)->kfile.file < 0 ) { error = HA_ERR_NO_SUCH_TABLE; } @@ -348,7 +348,7 @@ int _ma_readinfo(register MARIA_HA *info, int lock_type, int check_keybuffer) MARIA_SHARE *share=info->s; if (!share->tot_locks) { - if (_ma_state_info_read_dsk(share->kfile, &share->state, 1)) + if (_ma_state_info_read_dsk(share->kfile.file, &share->state, 1)) { int error=my_errno ? my_errno : -1; my_errno=error; @@ -390,13 +390,13 @@ int _ma_writeinfo(register MARIA_HA *info, uint operation) share->state.process= share->last_process= share->this_process; share->state.unique= info->last_unique= info->this_unique; share->state.update_count= info->last_loop= ++info->this_loop; - if ((error= _ma_state_info_write(share->kfile, &share->state, 1))) + if ((error= _ma_state_info_write(share->kfile.file, &share->state, 1))) olderror=my_errno; #ifdef __WIN__ if (maria_flush) { - _commit(share->kfile); - _commit(info->dfile); + _commit(share->kfile.file); + _commit(info->dfile.file); } #endif my_errno=olderror; @@ -420,7 +420,8 @@ int _ma_test_if_changed(register MARIA_HA *info) { /* Keyfile has changed */ DBUG_PRINT("info",("index file changed")); if (share->state.process != share->this_process) - VOID(flush_key_blocks(share->key_cache, share->kfile, FLUSH_RELEASE)); + VOID(flush_pagecache_blocks(share->pagecache, &share->kfile, + FLUSH_RELEASE)); share->last_process=share->state.process; info->last_unique= share->state.unique; info->last_loop= share->state.update_count; @@ -472,7 +473,7 @@ int _ma_mark_file_changed(MARIA_HA *info) { mi_int2store(buff,share->state.open_count); buff[2]=1; /* Mark that it's changed */ - DBUG_RETURN(my_pwrite(share->kfile,buff,sizeof(buff), + DBUG_RETURN(my_pwrite(share->kfile.file, buff, sizeof(buff), sizeof(share->state.header), MYF(MY_NABP))); } @@ -501,9 +502,9 @@ int _ma_decrement_open_count(MARIA_HA *info) { share->state.open_count--; mi_int2store(buff,share->state.open_count); - write_error=my_pwrite(share->kfile,buff,sizeof(buff), - sizeof(share->state.header), - MYF(MY_NABP)); + write_error= my_pwrite(share->kfile.file, buff, sizeof(buff), + sizeof(share->state.header), + MYF(MY_NABP)); } if (!lock_error) lock_error=maria_lock_database(info,old_lock); diff --git a/storage/maria/ma_loghandler.c b/storage/maria/ma_loghandler.c index 1dc4e9171e3..5db7ce8b163 100644 --- a/storage/maria/ma_loghandler.c +++ b/storage/maria/ma_loghandler.c @@ -1367,6 +1367,7 @@ static my_bool translog_buffer_flush(struct st_translog_buffer *buffer) { PAGECACHE_FILE file; file.file= buffer->file; + DBUG_ASSERT(log_descriptor.pagecache->block_size == TRANSLOG_PAGE_SIZE); if (pagecache_write(log_descriptor.pagecache, &file, (LSN_OFFSET(buffer->offset) + i) / TRANSLOG_PAGE_SIZE, diff --git a/storage/maria/ma_loghandler.h b/storage/maria/ma_loghandler.h index 3646afcf52a..48101814063 100644 --- a/storage/maria/ma_loghandler.h +++ b/storage/maria/ma_loghandler.h @@ -146,37 +146,40 @@ struct st_translog_reader_data }; -my_bool translog_init(const char *directory, uint32 log_file_max_size, - uint32 server_version, uint32 server_id, - PAGECACHE *pagecache, uint flags); - -my_bool translog_write_record(LSN *lsn, - enum translog_record_type type, - SHORT_TRANSACTION_ID short_trid, - void *tcb, - translog_size_t part1_length, - byte *part1_buff, ...); - -void translog_destroy(); - -translog_size_t translog_read_record_header(LSN lsn, - TRANSLOG_HEADER_BUFFER *buff); - -void translog_free_record_header(TRANSLOG_HEADER_BUFFER *buff); - -translog_size_t translog_read_record(LSN lsn, - translog_size_t offset, - translog_size_t length, - byte *buffer, - struct st_translog_reader_data *data); - -my_bool translog_flush(LSN lsn); - -my_bool translog_init_scanner(LSN lsn, - my_bool fixed_horizon, - struct st_translog_scanner_data *scanner); - -translog_size_t translog_read_next_record_header(TRANSLOG_SCANNER_DATA - *scanner, - TRANSLOG_HEADER_BUFFER *buff); +extern my_bool translog_init(const char *directory, uint32 log_file_max_size, + uint32 server_version, uint32 server_id, + PAGECACHE *pagecache, uint flags); + +extern my_bool translog_write_record(LSN *lsn, + enum translog_record_type type, + SHORT_TRANSACTION_ID short_trid, + void *tcb, + translog_size_t part1_length, + byte *part1_buff, ...); + +extern void translog_destroy(); + +extern translog_size_t translog_read_record_header(LSN lsn, + TRANSLOG_HEADER_BUFFER + *buff); + +extern void translog_free_record_header(TRANSLOG_HEADER_BUFFER *buff); + +extern translog_size_t translog_read_record(LSN lsn, + translog_size_t offset, + translog_size_t length, + byte *buffer, + struct st_translog_reader_data + *data); + +extern my_bool translog_flush(LSN lsn); + +extern my_bool translog_init_scanner(LSN lsn, + my_bool fixed_horizon, + struct st_translog_scanner_data *scanner); + +extern translog_size_t translog_read_next_record_header(TRANSLOG_SCANNER_DATA + *scanner, + TRANSLOG_HEADER_BUFFER + *buff); diff --git a/storage/maria/ma_open.c b/storage/maria/ma_open.c index 19113196f15..96b2971aab6 100644 --- a/storage/maria/ma_open.c +++ b/storage/maria/ma_open.c @@ -110,8 +110,8 @@ MARIA_HA *maria_open(const char *name, int mode, uint open_flags) bzero((gptr) &share_buff,sizeof(share_buff)); share_buff.state.rec_per_key_part=rec_per_key_part; share_buff.state.key_root=key_root; - share_buff.key_cache= multi_key_cache_search(name_buff, strlen(name_buff), - maria_key_cache); + share_buff.pagecache= multi_pagecache_search(name_buff, strlen(name_buff), + maria_pagecache); DBUG_EXECUTE_IF("maria_pretend_crashed_table_on_open", if (strstr(name, "/t1")) @@ -449,7 +449,7 @@ MARIA_HA *maria_open(const char *name, int mode, uint open_flags) goto err; errpos= 5; - share->kfile=kfile; + share->kfile.file= kfile; share->this_process=(ulong) getpid(); share->last_process= share->state.process; share->base.key_parts=key_parts; @@ -463,7 +463,7 @@ MARIA_HA *maria_open(const char *name, int mode, uint open_flags) share->block_size= share->base.block_size; my_afree((gptr) disk_cache); _ma_setup_functions(share); - if ((*share->once_init)(share, info.dfile)) + if ((*share->once_init)(share, info.dfile.file)) goto err; share->is_log_table= FALSE; #ifdef THREAD @@ -505,8 +505,8 @@ MARIA_HA *maria_open(const char *name, int mode, uint open_flags) goto err; } if (share->data_file_type == BLOCK_RECORD) - info.dfile= share->bitmap.file; - else if (_ma_open_datafile(&info, share, old_info->dfile)) + info.dfile.file= share->bitmap.file; + else if (_ma_open_datafile(&info, share, old_info->dfile.file)) goto err; errpos= 5; have_rtree= old_info->maria_rtree_recursion_state != NULL; @@ -537,7 +537,7 @@ MARIA_HA *maria_open(const char *name, int mode, uint open_flags) info.cur_row.lastpos= HA_OFFSET_ERROR; info.update= (short) (HA_STATE_NEXT_FOUND+HA_STATE_PREV_FOUND); info.opt_flag=READ_CHECK_USED; - info.this_unique= (ulong) info.dfile; /* Uniq number in process */ + info.this_unique= (ulong) info.dfile.file; /* Uniq number in process */ if (share->data_file_type == COMPRESSED_RECORD) info.this_unique= share->state.unique; info.this_loop=0; /* Update counter */ @@ -614,7 +614,7 @@ err: /* fall through */ case 5: if (share->data_file_type != BLOCK_RECORD) - VOID(my_close(info.dfile,MYF(0))); + VOID(my_close(info.dfile.file, MYF(0))); if (old_info) break; /* Don't remove open table */ (*share->once_end)(share); @@ -1187,15 +1187,16 @@ char *_ma_recinfo_read(char *ptr, MARIA_COLUMNDEF *recinfo) int _ma_open_datafile(MARIA_HA *info, MARIA_SHARE *share, File file_to_dup __attribute__((unused))) { - info->dfile= my_open(share->data_file_name, share->mode | O_SHARE, - MYF(MY_WME)); - return info->dfile >= 0 ? 0 : 1; + info->dfile.file= my_open(share->data_file_name, share->mode | O_SHARE, + MYF(MY_WME)); + return info->dfile.file >= 0 ? 0 : 1; } int _ma_open_keyfile(MARIA_SHARE *share) { - if ((share->kfile=my_open(share->unique_file_name, share->mode | O_SHARE, + if ((share->kfile.file= my_open(share->unique_file_name, + share->mode | O_SHARE, MYF(MY_WME))) < 0) return 1; return 0; diff --git a/storage/maria/ma_packrec.c b/storage/maria/ma_packrec.c index 7c875e7b91d..30b7d0b0eec 100644 --- a/storage/maria/ma_packrec.c +++ b/storage/maria/ma_packrec.c @@ -483,7 +483,7 @@ int _ma_read_pack_record(MARIA_HA *info, byte *buf, MARIA_RECORD_POS filepos) if (filepos == HA_OFFSET_ERROR) DBUG_RETURN(-1); /* _search() didn't find record */ - file=info->dfile; + file= info->dfile.file; if (_ma_pack_get_block_info(info, &info->bit_buff, &block_info, &info->rec_buff, &info->rec_buff_size, file, filepos)) @@ -1064,7 +1064,7 @@ int _ma_read_rnd_pack_record(MARIA_HA *info, goto err; } - file= info->dfile; + file= info->dfile.file; if (info->opt_flag & READ_CACHE_USED) { if (_ma_read_cache(&info->rec_cache, (byte*) block_info.header, @@ -1094,7 +1094,7 @@ int _ma_read_rnd_pack_record(MARIA_HA *info, } else { - if (my_read(info->dfile,(byte*) info->rec_buff + block_info.offset, + if (my_read(info->dfile.file, (byte*)info->rec_buff + block_info.offset, block_info.rec_len-block_info.offset, MYF(MY_NABP))) goto err; @@ -1250,7 +1250,7 @@ my_bool _ma_memmap_file(MARIA_HA *info) if (!info->s->file_map) { - if (my_seek(info->dfile,0L,MY_SEEK_END,MYF(0)) < + if (my_seek(info->dfile.file, 0L, MY_SEEK_END, MYF(0)) < share->state.state.data_file_length+MEMMAP_EXTRA_MARGIN) { DBUG_PRINT("warning",("File isn't extended for memmap")); diff --git a/storage/maria/ma_page.c b/storage/maria/ma_page.c index d0a11ad08ab..96907e0ffb0 100644 --- a/storage/maria/ma_page.c +++ b/storage/maria/ma_page.c @@ -29,14 +29,20 @@ byte *_ma_fetch_keypage(register MARIA_HA *info, MARIA_KEYDEF *keyinfo, DBUG_ENTER("_ma_fetch_keypage"); DBUG_PRINT("enter",("page: %ld", (long) page)); - tmp= key_cache_read(info->s->key_cache, info->s->kfile, page, level, buff, - info->s->block_size, info->s->block_size, - return_buffer); + DBUG_ASSERT(info->s->pagecache->block_size == keyinfo->block_length && + info->s->pagecache->block_size == info->s->block_size); + /* + TODO: replace PAGECACHE_PLAIN_PAGE with PAGECACHE_LSN_PAGE when + LSN on the pages will be implemented + */ + tmp= pagecache_read(info->s->pagecache, &info->s->kfile, + page / keyinfo->block_length, level, buff, + PAGECACHE_PLAIN_PAGE, PAGECACHE_LOCK_LEFT_UNLOCKED, 0); if (tmp == info->buff) info->keybuff_used=1; else if (!tmp) { - DBUG_PRINT("error",("Got errno: %d from key_cache_read",my_errno)); + DBUG_PRINT("error",("Got errno: %d from pagecache_read",my_errno)); info->last_keypage=HA_OFFSET_ERROR; maria_print_error(info->s, HA_ERR_CRASHED); my_errno=HA_ERR_CRASHED; @@ -63,7 +69,6 @@ byte *_ma_fetch_keypage(register MARIA_HA *info, MARIA_KEYDEF *keyinfo, int _ma_write_keypage(register MARIA_HA *info, register MARIA_KEYDEF *keyinfo, my_off_t page, int level, byte *buff) { - reg3 uint length; DBUG_ENTER("_ma_write_keypage"); #ifndef FAST /* Safety check */ @@ -71,7 +76,8 @@ int _ma_write_keypage(register MARIA_HA *info, register MARIA_KEYDEF *keyinfo, page+keyinfo->block_length > info->state->key_file_length || (page & (MARIA_MIN_KEY_BLOCK_LENGTH-1))) { - DBUG_PRINT("error",("Trying to write inside key status region: key_start: %lu length: %lu page: %lu", + DBUG_PRINT("error",("Trying to write inside key status region: " + "key_start: %lu length: %lu page: %lu", (long) info->s->base.keystart, (long) info->state->key_file_length, (long) page)); @@ -82,21 +88,18 @@ int _ma_write_keypage(register MARIA_HA *info, register MARIA_KEYDEF *keyinfo, DBUG_DUMP("buff",(byte*) buff,maria_getint(buff)); #endif - if ((length=keyinfo->block_length) > IO_SIZE*2 && - info->state->key_file_length != page+length) - length= ((maria_getint(buff)+IO_SIZE-1) & (uint) ~(IO_SIZE-1)); -#ifdef HAVE_purify - { - length=maria_getint(buff); - bzero((byte*) buff+length,keyinfo->block_length-length); - length=keyinfo->block_length; - } -#endif - DBUG_RETURN((key_cache_write(info->s->key_cache, - info->s->kfile,page, level, (byte*) buff,length, - (uint) keyinfo->block_length, - (int) ((info->lock_type != F_UNLCK) || - info->s->delay_key_write)))); + DBUG_ASSERT(info->s->pagecache->block_size == keyinfo->block_length); + DBUG_ASSERT(info->s->pagecache->block_size == info->s->block_size); + /* + TODO: replace PAGECACHE_PLAIN_PAGE with PAGECACHE_LSN_PAGE when + LSN on the pages will be implemented + */ + DBUG_RETURN(pagecache_write(info->s->pagecache, + &info->s->kfile, page / keyinfo->block_length, + level, buff, PAGECACHE_PLAIN_PAGE, + PAGECACHE_LOCK_LEFT_UNLOCKED, + PAGECACHE_PIN_LEFT_PINNED, + PAGECACHE_WRITE_DELAY, 0)); } /* maria_write_keypage */ @@ -107,18 +110,31 @@ int _ma_dispose(register MARIA_HA *info, MARIA_KEYDEF *keyinfo, my_off_t pos, { my_off_t old_link; char buff[8]; + uint offset; + pgcache_page_no_t page_no; DBUG_ENTER("_ma_dispose"); DBUG_PRINT("enter",("pos: %ld", (long) pos)); old_link= info->s->state.key_del; info->s->state.key_del= pos; + page_no= pos / keyinfo->block_length; + offset= pos % keyinfo->block_length; mi_sizestore(buff,old_link); info->s->state.changed|= STATE_NOT_SORTED_PAGES; - DBUG_RETURN(key_cache_write(info->s->key_cache, - info->s->kfile, pos , level, buff, - sizeof(buff), - (uint) keyinfo->block_length, - (int) (info->lock_type != F_UNLCK))); + + DBUG_ASSERT(info->s->pagecache->block_size == keyinfo->block_length && + info->s->pagecache->block_size == info->s->block_size); + /* + TODO: replace PAGECACHE_PLAIN_PAGE with PAGECACHE_LSN_PAGE when + LSN on the pages will be implemented + */ + DBUG_RETURN(pagecache_write_part(info->s->pagecache, + &info->s->kfile, page_no, level, buff, + PAGECACHE_PLAIN_PAGE, + PAGECACHE_LOCK_LEFT_UNLOCKED, + PAGECACHE_PIN_LEFT_PINNED, + PAGECACHE_WRITE_DELAY, 0, + offset, sizeof(buff))); } /* _ma_dispose */ @@ -143,11 +159,17 @@ my_off_t _ma_new(register MARIA_HA *info, MARIA_KEYDEF *keyinfo, int level) } else { - if (!key_cache_read(info->s->key_cache, - info->s->kfile, pos, level, - buff, - (uint) sizeof(buff), - (uint) keyinfo->block_length,0)) + DBUG_ASSERT(info->s->pagecache->block_size == keyinfo->block_length && + info->s->pagecache->block_size == info->s->block_size); + /* + TODO: replace PAGECACHE_PLAIN_PAGE with PAGECACHE_LSN_PAGE when + LSN on the pages will be implemented + */ + DBUG_ASSERT(info->s->pagecache->block_size == keyinfo->block_length); + if (!pagecache_read(info->s->pagecache, + &info->s->kfile, pos / keyinfo->block_length, level, + buff, PAGECACHE_PLAIN_PAGE, + PAGECACHE_LOCK_LEFT_UNLOCKED, 0)) pos= HA_OFFSET_ERROR; else info->s->state.key_del= mi_sizekorr(buff); diff --git a/mysys/mf_pagecache.c b/storage/maria/ma_pagecache.c index 1b9d48c80e6..ea63210ce95 100755 --- a/mysys/mf_pagecache.c +++ b/storage/maria/ma_pagecache.c @@ -29,7 +29,7 @@ to disk, if necessary. This is handled in find_block(). With the new free list, the blocks can have three temperatures: hot, warm and cold (which is free). This is remembered in the block header - by the enum BLOCK_TEMPERATURE temperature variable. Remembering the + by the enum PCBLOCK_TEMPERATURE temperature variable. Remembering the temperature is necessary to correctly count the number of warm blocks, which is required to decide when blocks are allowed to become hot. Whenever a block is inserted to another (sub-)chain, we take the old and new @@ -39,10 +39,9 @@ as such gives the maximum number of in-use blocks at any time. */ -#include "mysys_priv.h" +#include "maria_def.h" #include <m_string.h> #include <pagecache.h> -#include "my_static.h" #include <my_bit.h> #include <errno.h> #include <stdarg.h> @@ -94,7 +93,7 @@ */ #define SERIALIZED_READ_FROM_CACHE yes -#define BLOCK_INFO(B) \ +#define PCBLOCK_INFO(B) \ DBUG_PRINT("info", \ ("block 0x%lx file %lu page %lu s %0x hshL 0x%lx req %u/%u " \ "wrlock: %c", \ @@ -111,7 +110,7 @@ (uint)((B)->hash_link ? \ (B)->hash_link->requests : \ 0), \ - ((block->status & BLOCK_WRLOCK)?'Y':'N'))) + ((block->status & PCBLOCK_WRLOCK)?'Y':'N'))) /* TODO: put it to my_static.c */ my_bool my_disable_flush_pagecache_blocks= 0; @@ -147,13 +146,13 @@ struct st_pagecache_hash_link }; /* simple states of a block */ -#define BLOCK_ERROR 1 /* an error occurred when performing disk i/o */ -#define BLOCK_READ 2 /* the is page in the block buffer */ -#define BLOCK_IN_SWITCH 4 /* block is preparing to read new page */ -#define BLOCK_REASSIGNED 8 /* block does not accept requests for old page */ -#define BLOCK_IN_FLUSH 16 /* block is in flush operation */ -#define BLOCK_CHANGED 32 /* block buffer contains a dirty page */ -#define BLOCK_WRLOCK 64 /* write locked block */ +#define PCBLOCK_ERROR 1 /* an error occurred when performing disk i/o */ +#define PCBLOCK_READ 2 /* the is page in the block buffer */ +#define PCBLOCK_IN_SWITCH 4 /* block is preparing to read new page */ +#define PCBLOCK_REASSIGNED 8 /* block does not accept requests for old page */ +#define PCBLOCK_IN_FLUSH 16 /* block is in flush operation */ +#define PCBLOCK_CHANGED 32 /* block buffer contains a dirty page */ +#define PCBLOCK_WRLOCK 64 /* write locked block */ /* page status, returned by find_block */ #define PAGE_READ 0 @@ -161,7 +160,7 @@ struct st_pagecache_hash_link #define PAGE_WAIT_TO_BE_READ 2 /* block temperature determines in which (sub-)chain the block currently is */ -enum BLOCK_TEMPERATURE { BLOCK_COLD /*free*/ , BLOCK_WARM , BLOCK_HOT }; +enum PCBLOCK_TEMPERATURE { PCBLOCK_COLD /*free*/ , PCBLOCK_WARM , PCBLOCK_HOT }; /* debug info */ #ifndef DBUG_OFF @@ -294,7 +293,7 @@ struct st_pagecache_block_link PAGECACHE_PIN_INFO *pin_list; PAGECACHE_LOCK_INFO *lock_list; #endif - enum BLOCK_TEMPERATURE temperature; /* block temperature: cold, warm, hot */ + enum PCBLOCK_TEMPERATURE temperature; /* block temperature: cold, warm, hot */ enum pagecache_page_type type; /* type of the block */ uint hits_left; /* number of hits left until promotion */ ulonglong last_hit_time; /* timestamp of the last hit */ @@ -302,6 +301,9 @@ struct st_pagecache_block_link KEYCACHE_CONDVAR *condvar; /* condition variable for 'no readers' event */ }; +PAGECACHE dflt_pagecache_var; +PAGECACHE *dflt_pagecache= &dflt_pagecache_var; + #ifdef PAGECACHE_DEBUG /* debug checks */ static my_bool info_check_pin(PAGECACHE_BLOCK_LINK *block, @@ -506,7 +508,7 @@ static long pagecache_thread_id; #define KEYCACHE_THREAD_TRACE(l) #endif /* defined(PAGECACHE_DEBUG) || !defined(DBUG_OFF) */ -#define BLOCK_NUMBER(p, b) \ +#define PCBLOCK_NUMBER(p, b) \ ((uint) (((char*)(b)-(char *) p->block_root)/sizeof(PAGECACHE_BLOCK_LINK))) #define PAGECACHE_HASH_LINK_NUMBER(p, h) \ ((uint) (((char*)(h)-(char *) p->hash_link_root)/ \ @@ -1096,9 +1098,9 @@ static void link_to_file_list(PAGECACHE *pagecache, if (unlink) unlink_changed(block); link_changed(block, &pagecache->file_blocks[FILE_HASH(*file)]); - if (block->status & BLOCK_CHANGED) + if (block->status & PCBLOCK_CHANGED) { - block->status&= ~BLOCK_CHANGED; + block->status&= ~PCBLOCK_CHANGED; block->rec_lsn= 0; pagecache->blocks_changed--; pagecache->global_blocks_changed--; @@ -1117,7 +1119,7 @@ static inline void link_to_changed_list(PAGECACHE *pagecache, unlink_changed(block); link_changed(block, &pagecache->changed_blocks[FILE_HASH(block->hash_link->file)]); - block->status|=BLOCK_CHANGED; + block->status|=PCBLOCK_CHANGED; pagecache->blocks_changed++; pagecache->global_blocks_changed++; } @@ -1165,7 +1167,7 @@ static void link_block(PAGECACHE *pagecache, PAGECACHE_BLOCK_LINK *block, PAGECACHE_BLOCK_LINK *ins; PAGECACHE_BLOCK_LINK **ptr_ins; - BLOCK_INFO(block); + PCBLOCK_INFO(block); KEYCACHE_DBUG_ASSERT(! (block->hash_link && block->hash_link->requests)); #ifdef THREAD if (!hot && pagecache->waiting_for_block.last_thread) @@ -1200,7 +1202,7 @@ static void link_block(PAGECACHE *pagecache, PAGECACHE_BLOCK_LINK *block, #if defined(PAGECACHE_DEBUG) KEYCACHE_DBUG_PRINT("link_block", ("linked,unlinked block %u status=%x #requests=%u #available=%u", - BLOCK_NUMBER(pagecache, block), block->status, + PCBLOCK_NUMBER(pagecache, block), block->status, block->requests, pagecache->blocks_available)); #endif return; @@ -1231,7 +1233,7 @@ static void link_block(PAGECACHE *pagecache, PAGECACHE_BLOCK_LINK *block, pagecache->blocks_available++; KEYCACHE_DBUG_PRINT("link_block", ("linked block %u:%1u status=%x #requests=%u #available=%u", - BLOCK_NUMBER(pagecache, block), at_end, block->status, + PCBLOCK_NUMBER(pagecache, block), at_end, block->status, block->requests, pagecache->blocks_available)); KEYCACHE_DBUG_ASSERT((ulong) pagecache->blocks_available <= pagecache->blocks_used); @@ -1280,9 +1282,9 @@ static void unlink_block(PAGECACHE *pagecache, PAGECACHE_BLOCK_LINK *block) pagecache->blocks_available--; KEYCACHE_DBUG_PRINT("unlink_block", ("unlinked block 0x%lx (%u) status=%x #requests=%u #available=%u", - (ulong)block, BLOCK_NUMBER(pagecache, block), block->status, + (ulong)block, PCBLOCK_NUMBER(pagecache, block), block->status, block->requests, pagecache->blocks_available)); - BLOCK_INFO(block); + PCBLOCK_INFO(block); #endif DBUG_VOID_RETURN; } @@ -1306,9 +1308,9 @@ static void reg_requests(PAGECACHE *pagecache, PAGECACHE_BLOCK_LINK *block, { DBUG_ENTER("reg_requests"); DBUG_PRINT("enter", ("block 0x%lx (%u) status=%x, reqs: %u", - (ulong)block, BLOCK_NUMBER(pagecache, block), + (ulong)block, PCBLOCK_NUMBER(pagecache, block), block->status, block->requests)); - BLOCK_INFO(block); + PCBLOCK_INFO(block); if (! block->requests) /* First request for the block unlinks it */ unlink_block(pagecache, block); @@ -1351,9 +1353,9 @@ static void unreg_request(PAGECACHE *pagecache, { DBUG_ENTER("unreg_request"); DBUG_PRINT("enter", ("block 0x%lx (%u) status=%x, reqs: %u", - (ulong)block, BLOCK_NUMBER(pagecache, block), + (ulong)block, PCBLOCK_NUMBER(pagecache, block), block->status, block->requests)); - BLOCK_INFO(block); + PCBLOCK_INFO(block); DBUG_ASSERT(block->requests > 0); if (! --block->requests) { @@ -1364,9 +1366,9 @@ static void unreg_request(PAGECACHE *pagecache, pagecache->warm_blocks > pagecache->min_warm_blocks; if (hot) { - if (block->temperature == BLOCK_WARM) + if (block->temperature == PCBLOCK_WARM) pagecache->warm_blocks--; - block->temperature= BLOCK_HOT; + block->temperature= PCBLOCK_HOT; KEYCACHE_DBUG_PRINT("unreg_request", ("#warm_blocks: %lu", pagecache->warm_blocks)); } @@ -1381,10 +1383,10 @@ static void unreg_request(PAGECACHE *pagecache, { unlink_block(pagecache, block); link_block(pagecache, block, 0, 0); - if (block->temperature != BLOCK_WARM) + if (block->temperature != PCBLOCK_WARM) { pagecache->warm_blocks++; - block->temperature= BLOCK_WARM; + block->temperature= PCBLOCK_WARM; } KEYCACHE_DBUG_PRINT("unreg_request", ("#warm_blocks: %lu", pagecache->warm_blocks)); @@ -1400,7 +1402,7 @@ static void unreg_request(PAGECACHE *pagecache, static inline void remove_reader(PAGECACHE_BLOCK_LINK *block) { DBUG_ENTER("remove_reader"); - BLOCK_INFO(block); + PCBLOCK_INFO(block); DBUG_ASSERT(block->hash_link->requests > 0); #ifdef THREAD if (! --block->hash_link->requests && block->condvar) @@ -1427,7 +1429,7 @@ static inline void wait_for_readers(PAGECACHE *pagecache { KEYCACHE_DBUG_PRINT("wait_for_readers: wait", ("suspend thread %ld block %u", - thread->id, BLOCK_NUMBER(pagecache, block))); + thread->id, PCBLOCK_NUMBER(pagecache, block))); block->condvar= &thread->suspend; pagecache_pthread_cond_wait(&thread->suspend, &pagecache->cache_lock); block->condvar= NULL; @@ -1677,7 +1679,7 @@ restart: PAGE_READ - if page already in the block, PAGE_TO_BE_READ - if it is to be read yet by the current thread WAIT_TO_BE_READ - if it is to be read by another thread - If an error occurs THE BLOCK_ERROR bit is set in the block status. + If an error occurs THE PCBLOCK_ERROR bit is set in the block status. It might happen that there are no blocks in LRU chain (in warm part) - all blocks are unlinked for some read/write operations. Then the function waits until first of this operations links any block back. @@ -1714,7 +1716,7 @@ restart: page_status= -1; if ((block= hash_link->block) && - block->hash_link == hash_link && (block->status & BLOCK_READ)) + block->hash_link == hash_link && (block->status & PCBLOCK_READ)) page_status= PAGE_READ; if (wrmode && pagecache->resize_in_flush) @@ -1729,7 +1731,7 @@ restart: unlink_hash(pagecache, hash_link); return 0; } - if (!(block->status & BLOCK_IN_FLUSH)) + if (!(block->status & PCBLOCK_IN_FLUSH)) { DBUG_ASSERT(hash_link->requests > 0); hash_link->requests--; @@ -1741,7 +1743,7 @@ restart: have unfinished readers of other key parts in the block buffer. Still we are guaranteed not to have any readers of the key part we are writing into until the block is - removed from the cache as we set the BLOCK_REASSIGNED + removed from the cache as we set the PCBLOCK_REASSIGNED flag (see the code below that handles reading requests). */ free_block(pagecache, block); @@ -1780,20 +1782,20 @@ restart: } if (page_status == PAGE_READ && - (block->status & (BLOCK_IN_SWITCH | BLOCK_REASSIGNED))) + (block->status & (PCBLOCK_IN_SWITCH | PCBLOCK_REASSIGNED))) { /* This is a request for a page to be removed from cache */ KEYCACHE_DBUG_PRINT("find_block", ("request for old page in block %u " "wrmode: %d block->status: %d", - BLOCK_NUMBER(pagecache, block), wrmode, + PCBLOCK_NUMBER(pagecache, block), wrmode, block->status)); /* Only reading requests can proceed until the old dirty page is flushed, all others are to be suspended, then resubmitted */ - if (!wrmode && !(block->status & BLOCK_REASSIGNED)) + if (!wrmode && !(block->status & PCBLOCK_REASSIGNED)) { if (reg_req) reg_requests(pagecache, block, 1); @@ -1829,7 +1831,7 @@ restart: /* Resubmit the request */ goto restart; } - block->status&= ~BLOCK_IN_SWITCH; + block->status&= ~PCBLOCK_IN_SWITCH; } else { @@ -1857,14 +1859,14 @@ restart: pagecache->blocks_used++; } pagecache->blocks_unused--; - DBUG_ASSERT((block->status & BLOCK_WRLOCK) == 0); + DBUG_ASSERT((block->status & PCBLOCK_WRLOCK) == 0); DBUG_ASSERT(block->pins == 0); block->status= 0; #ifndef DBUG_OFF block->type= PAGECACHE_EMPTY_PAGE; #endif block->requests= 1; - block->temperature= BLOCK_COLD; + block->temperature= PCBLOCK_COLD; block->hits_left= init_hits_left; block->last_hit_time= 0; link_to_file_list(pagecache, block, file, 0); @@ -1875,7 +1877,7 @@ restart: (ulong)block)); KEYCACHE_DBUG_PRINT("find_block", ("got free or never used block %u", - BLOCK_NUMBER(pagecache, block))); + PCBLOCK_NUMBER(pagecache, block))); } else { @@ -1920,23 +1922,23 @@ restart: reg_requests(pagecache, block, 1); hash_link->block= block; } - BLOCK_INFO(block); - DBUG_ASSERT((block->status & BLOCK_WRLOCK) == 0); + PCBLOCK_INFO(block); + DBUG_ASSERT((block->status & PCBLOCK_WRLOCK) == 0); DBUG_ASSERT(block->pins == 0); if (block->hash_link != hash_link && - ! (block->status & BLOCK_IN_SWITCH) ) + ! (block->status & PCBLOCK_IN_SWITCH) ) { /* this is a primary request for a new page */ - DBUG_ASSERT((block->status & BLOCK_WRLOCK) == 0); + DBUG_ASSERT((block->status & PCBLOCK_WRLOCK) == 0); DBUG_ASSERT(block->pins == 0); - block->status|= (BLOCK_IN_SWITCH | BLOCK_WRLOCK); + block->status|= (PCBLOCK_IN_SWITCH | PCBLOCK_WRLOCK); KEYCACHE_DBUG_PRINT("find_block", ("got block %u for new page", - BLOCK_NUMBER(pagecache, block))); + PCBLOCK_NUMBER(pagecache, block))); - if (block->status & BLOCK_CHANGED) + if (block->status & PCBLOCK_CHANGED) { /* The block contains a dirty page - push it out of the cache */ @@ -1958,7 +1960,7 @@ restart: pagecache->global_cache_write++; } - block->status|= BLOCK_REASSIGNED; + block->status|= PCBLOCK_REASSIGNED; if (block->hash_link) { /* @@ -1979,8 +1981,8 @@ restart: } link_to_file_list(pagecache, block, file, (my_bool)(block->hash_link ? 1 : 0)); - BLOCK_INFO(block); - block->status= error? BLOCK_ERROR : 0; + PCBLOCK_INFO(block); + block->status= error? PCBLOCK_ERROR : 0; #ifndef DBUG_OFF block->type= PAGECACHE_EMPTY_PAGE; #endif @@ -2000,7 +2002,7 @@ restart: "block->status: %u", block->hash_link, hash_link, block->status )); page_status= (((block->hash_link == hash_link) && - (block->status & BLOCK_READ)) ? + (block->status & PCBLOCK_READ)) ? PAGE_READ : PAGE_WAIT_TO_BE_READ); } } @@ -2015,7 +2017,7 @@ restart: "block->status: %u", block->hash_link, hash_link, block->status )); page_status= (((block->hash_link == hash_link) && - (block->status & BLOCK_READ)) ? + (block->status & PCBLOCK_READ)) ? PAGE_READ : PAGE_WAIT_TO_BE_READ); } } @@ -2047,7 +2049,7 @@ static void add_pin(PAGECACHE_BLOCK_LINK *block) DBUG_PRINT("enter", ("block 0x%lx pins: %u", (ulong) block, block->pins)); - BLOCK_INFO(block); + PCBLOCK_INFO(block); block->pins++; #ifdef PAGECACHE_DEBUG { @@ -2066,7 +2068,7 @@ static void remove_pin(PAGECACHE_BLOCK_LINK *block) DBUG_PRINT("enter", ("block 0x%lx pins: %u", (ulong) block, block->pins)); - BLOCK_INFO(block); + PCBLOCK_INFO(block); DBUG_ASSERT(block->pins > 0); block->pins--; #ifdef PAGECACHE_DEBUG @@ -2136,8 +2138,8 @@ static my_bool get_wrlock(PAGECACHE *pagecache, (ulong)block, file.file, block->hash_link->file.file, pageno, block->hash_link->pageno)); - BLOCK_INFO(block); - while (block->status & BLOCK_WRLOCK) + PCBLOCK_INFO(block); + while (block->status & PCBLOCK_WRLOCK) { /* Lock failed we will wait */ #ifdef THREAD @@ -2156,8 +2158,8 @@ static my_bool get_wrlock(PAGECACHE *pagecache, #else DBUG_ASSERT(0); #endif - BLOCK_INFO(block); - if ((block->status & (BLOCK_REASSIGNED | BLOCK_IN_SWITCH)) || + PCBLOCK_INFO(block); + if ((block->status & (PCBLOCK_REASSIGNED | PCBLOCK_IN_SWITCH)) || file.file != block->hash_link->file.file || pageno != block->hash_link->pageno) { @@ -2171,7 +2173,7 @@ static my_bool get_wrlock(PAGECACHE *pagecache, } DBUG_ASSERT(block->pins == 0); /* we are doing it by global cache mutex protection, so it is OK */ - block->status|= BLOCK_WRLOCK; + block->status|= PCBLOCK_WRLOCK; DBUG_PRINT("info", ("WR lock set, block 0x%lx", (ulong)block)); DBUG_RETURN(0); } @@ -2192,17 +2194,17 @@ static my_bool get_wrlock(PAGECACHE *pagecache, static void release_wrlock(PAGECACHE_BLOCK_LINK *block) { DBUG_ENTER("release_wrlock"); - BLOCK_INFO(block); - DBUG_ASSERT(block->status & BLOCK_WRLOCK); + PCBLOCK_INFO(block); + DBUG_ASSERT(block->status & PCBLOCK_WRLOCK); DBUG_ASSERT(block->pins > 0); - block->status&= ~BLOCK_WRLOCK; + block->status&= ~PCBLOCK_WRLOCK; DBUG_PRINT("info", ("WR lock reset, block 0x%lx", (ulong)block)); #ifdef THREAD /* release all threads waiting for write lock */ if (block->wqueue[COND_FOR_WRLOCK].last_thread) wqueue_release_queue(&block->wqueue[COND_FOR_WRLOCK]); #endif - BLOCK_INFO(block); + PCBLOCK_INFO(block); DBUG_VOID_RETURN; } @@ -2229,12 +2231,12 @@ static my_bool make_lock_and_pin(PAGECACHE *pagecache, { DBUG_ENTER("make_lock_and_pin"); DBUG_PRINT("enter", ("block: 0x%lx (%u), wrlock: %c pins: %u, lock %s, pin: %s", - (ulong)block, BLOCK_NUMBER(pagecache, block), - ((block->status & BLOCK_WRLOCK)?'Y':'N'), + (ulong)block, PCBLOCK_NUMBER(pagecache, block), + ((block->status & PCBLOCK_WRLOCK)?'Y':'N'), block->pins, page_cache_page_lock_str[lock], page_cache_page_pin_str[pin])); - BLOCK_INFO(block); + PCBLOCK_INFO(block); #ifdef PAGECACHE_DEBUG DBUG_ASSERT(info_check_pin(block, pin) == 0 && info_check_lock(block, lock, pin) == 0); @@ -2291,16 +2293,16 @@ static my_bool make_lock_and_pin(PAGECACHE *pagecache, DBUG_ASSERT(0); /* Never should happened */ } - BLOCK_INFO(block); + PCBLOCK_INFO(block); DBUG_RETURN(0); retry: DBUG_PRINT("INFO", ("Retry block 0x%lx", (ulong)block)); - BLOCK_INFO(block); + PCBLOCK_INFO(block); DBUG_ASSERT(block->hash_link->requests > 0); block->hash_link->requests--; DBUG_ASSERT(block->requests > 0); unreg_request(pagecache, block, 1); - BLOCK_INFO(block); + PCBLOCK_INFO(block); DBUG_RETURN(1); } @@ -2325,7 +2327,7 @@ retry: The function either reads a page data from file to the block buffer, or waits until another thread reads it. What page to read is determined by a block parameter - reference to a hash link for this page. - If an error occurs THE BLOCK_ERROR bit is set in the block status. + If an error occurs THE PCBLOCK_ERROR bit is set in the block status. */ static void read_block(PAGECACHE *pagecache, @@ -2360,13 +2362,13 @@ static void read_block(PAGECACHE *pagecache, block->hash_link->pageno, MYF(0)); pagecache_pthread_mutex_lock(&pagecache->cache_lock); if (got_length < pagecache->block_size) - block->status|= BLOCK_ERROR; + block->status|= PCBLOCK_ERROR; else - block->status= (BLOCK_READ | (block->status & BLOCK_WRLOCK)); + block->status= (PCBLOCK_READ | (block->status & PCBLOCK_WRLOCK)); if (validator != NULL && (*validator)(block->buffer, validator_data)) - block->status|= BLOCK_ERROR; + block->status|= PCBLOCK_ERROR; DBUG_PRINT("read_block", ("primary request: new page in cache")); @@ -2464,7 +2466,7 @@ void pagecache_unlock_page(PAGECACHE *pagecache, /* See NOTE for pagecache_unlock_page about registering requests */ block= find_block(pagecache, file, pageno, 0, 0, test(pin == PAGECACHE_PIN_LEFT_UNPINNED), &page_st); - BLOCK_INFO(block); + PCBLOCK_INFO(block); DBUG_ASSERT(block != 0 && page_st == PAGE_READ); if (first_REDO_LSN_for_page) { @@ -2820,7 +2822,7 @@ restart: DBUG_ASSERT(block->type == PAGECACHE_EMPTY_PAGE || block->type == type); block->type= type; - if (block->status != BLOCK_ERROR && page_st != PAGE_READ) + if (block->status != PCBLOCK_ERROR && page_st != PAGE_READ) { DBUG_PRINT("info", ("read block 0x%lx", (ulong)block)); /* The requested page is to be read into the block buffer */ @@ -2840,7 +2842,7 @@ restart: goto restart; } - if (! ((status= block->status) & BLOCK_ERROR)) + if (! ((status= block->status) & PCBLOCK_ERROR)) { #if !defined(SERIALIZED_READ_FROM_CACHE) pagecache_pthread_mutex_unlock(&pagecache->cache_lock); @@ -2870,7 +2872,7 @@ restart: pagecache_pthread_mutex_unlock(&pagecache->cache_lock); - if (status & BLOCK_ERROR) + if (status & PCBLOCK_ERROR) DBUG_RETURN((byte *) 0); DBUG_RETURN(buff); @@ -2960,14 +2962,14 @@ restart: goto restart; } - if (block->status & BLOCK_CHANGED) + if (block->status & PCBLOCK_CHANGED) { if (flush) { /* The block contains a dirty page - push it out of the cache */ - + KEYCACHE_DBUG_PRINT("find_block", ("block is dirty")); - + pagecache_pthread_mutex_unlock(&pagecache->cache_lock); /* The call is thread safe because only the current @@ -2982,10 +2984,10 @@ restart: MYF(MY_NABP | MY_WAIT_IF_FULL)); pagecache_pthread_mutex_lock(&pagecache->cache_lock); pagecache->global_cache_write++; - + if (error) { - block->status|= BLOCK_ERROR; + block->status|= PCBLOCK_ERROR; goto err; } } @@ -3087,45 +3089,39 @@ static struct write_pin_change write_pin_change_table[]= PAGECACHE_UNPIN} /*PAGECACHE_UNPIN*/ }; -my_bool pagecache_write(PAGECACHE *pagecache, - PAGECACHE_FILE *file, - pgcache_page_no_t pageno, - uint level, - byte *buff, - enum pagecache_page_type type, - enum pagecache_page_lock lock, - enum pagecache_page_pin pin, - enum pagecache_write_mode write_mode, - PAGECACHE_PAGE_LINK *link) +my_bool pagecache_write_part(PAGECACHE *pagecache, + PAGECACHE_FILE *file, + pgcache_page_no_t pageno, + uint level, + byte *buff, + enum pagecache_page_type type, + enum pagecache_page_lock lock, + enum pagecache_page_pin pin, + enum pagecache_write_mode write_mode, + PAGECACHE_PAGE_LINK *link, + uint offset, uint size) { - reg1 PAGECACHE_BLOCK_LINK *block= NULL; + PAGECACHE_BLOCK_LINK *block= NULL; PAGECACHE_PAGE_LINK fake_link; int error= 0; int need_lock_change= write_lock_change_table[lock].need_lock_change; - DBUG_ENTER("pagecache_write"); - DBUG_PRINT("enter", ("fd: %u page: %lu level: %u t:%s l%s p%s m%s", + DBUG_ENTER("pagecache_write_part"); + DBUG_PRINT("enter", ("fd: %u page: %lu level: %u type: %s lock: %s " + "pin: %s mode: %s offset: %u size %u", (uint) file->file, (ulong) pageno, level, page_cache_page_type_str[type], page_cache_page_lock_str[lock], page_cache_page_pin_str[pin], - page_cache_page_write_mode_str[write_mode])); + page_cache_page_write_mode_str[write_mode], + offset, size)); DBUG_ASSERT(lock != PAGECACHE_LOCK_LEFT_READLOCKED && lock != PAGECACHE_LOCK_READ_UNLOCK); + DBUG_ASSERT(offset + size <= pagecache->block_size); if (!link) link= &fake_link; else *link= 0; - if (write_mode == PAGECACHE_WRITE_NOW) - { - /* we allow direct write if we do not use long term lockings */ - DBUG_ASSERT(lock == PAGECACHE_LOCK_LEFT_UNLOCKED); - /* Force writing from buff into disk */ - pagecache->global_cache_write++; - if (pagecache_fwrite(pagecache, file, buff, pageno, type, - MYF(MY_NABP | MY_WAIT_IF_FULL))) - DBUG_RETURN(1); - } restart: #if !defined(DBUG_OFF) && defined(EXTRA_DEBUG) @@ -3188,11 +3184,14 @@ restart: if (write_mode == PAGECACHE_WRITE_DONE) { - if ((block->status & BLOCK_ERROR) && page_st != PAGE_READ) + if ((block->status & PCBLOCK_ERROR) && page_st != PAGE_READ) { /* Copy data from buff */ - bmove512(block->buffer, buff, pagecache->block_size); - block->status= (BLOCK_READ | (block->status & BLOCK_WRLOCK)); + if (!(size & 511)) + bmove512(block->buffer + offset, buff, size); + else + memcpy(block->buffer + offset, buff, size); + block->status= (PCBLOCK_READ | (block->status & PCBLOCK_WRLOCK)); KEYCACHE_DBUG_PRINT("key_cache_insert", ("primary request: new page in cache")); #ifdef THREAD @@ -3204,20 +3203,16 @@ restart: } else { - if (write_mode == PAGECACHE_WRITE_NOW) - { - /* buff has been written to disk at start */ - if ((block->status & BLOCK_CHANGED) && - !(block->status & BLOCK_ERROR)) - link_to_file_list(pagecache, block, &block->hash_link->file, 1); - } - else if (! (block->status & BLOCK_CHANGED)) + if (! (block->status & PCBLOCK_CHANGED)) link_to_changed_list(pagecache, block); - if (! (block->status & BLOCK_ERROR)) + if (! (block->status & PCBLOCK_ERROR)) { - bmove512(block->buffer, buff, pagecache->block_size); - block->status|= BLOCK_READ; + if (!(size & 511)) + bmove512(block->buffer + offset, buff, size); + else + memcpy(block->buffer + offset, buff, size); + block->status|= PCBLOCK_READ; } } @@ -3248,7 +3243,7 @@ restart: *link= (PAGECACHE_PAGE_LINK)block; - if (block->status & BLOCK_ERROR) + if (block->status & PCBLOCK_ERROR) error= 1; dec_counter_for_resize_op(pagecache); @@ -3274,7 +3269,10 @@ end: DBUG_EXECUTE("exec", test_key_cache(pagecache, "end of key_cache_write", 1);); #endif - BLOCK_INFO(block); + if (block) + PCBLOCK_INFO(block); + else + DBUG_PRINT("info", ("No block")); DBUG_RETURN(error); } @@ -3290,22 +3288,22 @@ static void free_block(PAGECACHE *pagecache, PAGECACHE_BLOCK_LINK *block) KEYCACHE_THREAD_TRACE("free block"); KEYCACHE_DBUG_PRINT("free_block", ("block %u to be freed, hash_link %p", - BLOCK_NUMBER(pagecache, block), block->hash_link)); + PCBLOCK_NUMBER(pagecache, block), block->hash_link)); if (block->hash_link) { /* While waiting for readers to finish, new readers might request the - block. But since we set block->status|= BLOCK_REASSIGNED, they + block. But since we set block->status|= PCBLOCK_REASSIGNED, they will wait on block->wqueue[COND_FOR_SAVED]. They must be signalled later. */ - block->status|= BLOCK_REASSIGNED; + block->status|= PCBLOCK_REASSIGNED; wait_for_readers(pagecache, block); unlink_hash(pagecache, block->hash_link); } unlink_changed(block); - DBUG_ASSERT((block->status & BLOCK_WRLOCK) == 0); + DBUG_ASSERT((block->status & PCBLOCK_WRLOCK) == 0); DBUG_ASSERT(block->pins == 0); block->status= 0; #ifndef DBUG_OFF @@ -3320,9 +3318,9 @@ static void free_block(PAGECACHE *pagecache, PAGECACHE_BLOCK_LINK *block) /* Remove the free block from the LRU ring. */ unlink_block(pagecache, block); - if (block->temperature == BLOCK_WARM) + if (block->temperature == PCBLOCK_WARM) pagecache->warm_blocks--; - block->temperature= BLOCK_COLD; + block->temperature= PCBLOCK_COLD; /* Insert the free block in the free list. */ block->next_used= pagecache->free_block_list; pagecache->free_block_list= block; @@ -3363,7 +3361,7 @@ static int flush_cached_blocks(PAGECACHE *pagecache, /* Don't lock the cache during the flush */ pagecache_pthread_mutex_unlock(&pagecache->cache_lock); /* - As all blocks referred in 'cache' are marked by BLOCK_IN_FLUSH + As all blocks referred in 'cache' are marked by PCBLOCK_IN_FLUSH we are guarunteed no thread will change them */ qsort((byte*) cache, count, sizeof(*cache), (qsort_cmp) cmp_sec_link); @@ -3377,16 +3375,16 @@ static int flush_cached_blocks(PAGECACHE *pagecache, { KEYCACHE_DBUG_PRINT("flush_cached_blocks", ("block %u (0x%lx) pinned", - BLOCK_NUMBER(pagecache, block), (ulong)block)); + PCBLOCK_NUMBER(pagecache, block), (ulong)block)); DBUG_PRINT("info", ("block %u (0x%lx) pinned", - BLOCK_NUMBER(pagecache, block), (ulong)block)); - BLOCK_INFO(block); + PCBLOCK_NUMBER(pagecache, block), (ulong)block)); + PCBLOCK_INFO(block); last_errno= -1; unreg_request(pagecache, block, 1); continue; } /* if the block is not pinned then it is not write locked */ - DBUG_ASSERT((block->status & BLOCK_WRLOCK) == 0); + DBUG_ASSERT((block->status & PCBLOCK_WRLOCK) == 0); DBUG_ASSERT(block->pins == 0); #ifndef DBUG_OFF { @@ -3401,13 +3399,13 @@ static int flush_cached_blocks(PAGECACHE *pagecache, KEYCACHE_DBUG_PRINT("flush_cached_blocks", ("block %u (0x%lx) to be flushed", - BLOCK_NUMBER(pagecache, block), (ulong)block)); + PCBLOCK_NUMBER(pagecache, block), (ulong)block)); DBUG_PRINT("info", ("block %u (0x%lx) to be flushed", - BLOCK_NUMBER(pagecache, block), (ulong)block)); - BLOCK_INFO(block); + PCBLOCK_NUMBER(pagecache, block), (ulong)block)); + PCBLOCK_INFO(block); pagecache_pthread_mutex_unlock(&pagecache->cache_lock); DBUG_PRINT("info", ("block %u (0x%lx) pins: %u", - BLOCK_NUMBER(pagecache, block), (ulong)block, + PCBLOCK_NUMBER(pagecache, block), (ulong)block, block->pins)); DBUG_ASSERT(block->pins == 1); error= pagecache_fwrite(pagecache, file, @@ -3424,7 +3422,7 @@ static int flush_cached_blocks(PAGECACHE *pagecache, pagecache->global_cache_write++; if (error) { - block->status|= BLOCK_ERROR; + block->status|= PCBLOCK_ERROR; if (!last_errno) last_errno= errno ? errno : -1; } @@ -3445,7 +3443,7 @@ static int flush_cached_blocks(PAGECACHE *pagecache, } else { - block->status&= ~BLOCK_IN_FLUSH; + block->status&= ~PCBLOCK_IN_FLUSH; link_to_file_list(pagecache, block, file, 1); unreg_request(pagecache, block, 1); } @@ -3548,9 +3546,9 @@ restart: other threads to use it for new pages and interfere with our sequence ot flushing dirty file pages */ - block->status|= BLOCK_IN_FLUSH; + block->status|= PCBLOCK_IN_FLUSH; - if (! (block->status & BLOCK_IN_SWITCH)) + if (! (block->status & PCBLOCK_IN_SWITCH)) { /* We care only for the blocks for which flushing was not @@ -3653,7 +3651,7 @@ restart: #endif next= block->next_changed; if (block->hash_link->file.file == file->file && - (! (block->status & BLOCK_CHANGED) + (! (block->status & PCBLOCK_CHANGED) || type == FLUSH_IGNORE_CHANGED)) { reg_requests(pagecache, block, 1); @@ -3802,13 +3800,13 @@ my_bool pagecache_collect_changed_blocks_with_lsn(PAGECACHE *pagecache, does it have to be == hash_link->block... ? */ DBUG_ASSERT(block->hash_link != NULL); - DBUG_ASSERT(block->status & BLOCK_CHANGED); + DBUG_ASSERT(block->status & PCBLOCK_CHANGED); if (block->type != PAGECACHE_LSN_PAGE) continue; /* no need to store it */ /* In the current pagecache, rec_lsn is not set correctly: 1) it is set on pagecache_unlock(), too late (a page is dirty - (BLOCK_CHANGED) since the first pagecache_write()). So in this + (PCBLOCK_CHANGED) since the first pagecache_write()). So in this scenario: thread1: thread2: write_REDO @@ -3972,7 +3970,7 @@ static void pagecache_dump(PAGECACHE *pagecache) { block= block->next_used; fprintf(pagecache_dump_file, - "block:%u, ", BLOCK_NUMBER(pagecache, block)); + "block:%u, ", PCBLOCK_NUMBER(pagecache, block)); } while (block != pagecache->used_last); } diff --git a/storage/maria/ma_pagecaches.c b/storage/maria/ma_pagecaches.c new file mode 100644 index 00000000000..e635709c11e --- /dev/null +++ b/storage/maria/ma_pagecaches.c @@ -0,0 +1,105 @@ +/* Copyright (C) 2003-2007 MySQL AB + + 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; either version 2 of the License, or + (at your option) any later version. + + 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 */ + +/* + Handling of multiple key caches + + The idea is to have a thread safe hash on the table name, + with a default key cache value that is returned if the table name is not in + the cache. +*/ + +#include "maria_def.h" +#include <pagecache.h> +#include <hash.h> +#include <m_string.h> +#include "../../mysys/my_safehash.h" + +/***************************************************************************** + Functions to handle the pagecache objects +*****************************************************************************/ + +/* Variable to store all key cache objects */ +static SAFE_HASH pagecache_hash; + + +my_bool multi_pagecache_init(void) +{ + return safe_hash_init(&pagecache_hash, 16, (byte*) dflt_pagecache); +} + + +void multi_pagecache_free(void) +{ + safe_hash_free(&pagecache_hash); +} + +/* + Get a key cache to be used for a specific table. + + SYNOPSIS + multi_pagecache_search() + key key to find (usually table path) + uint length Length of key. + def Default value if no key cache + + NOTES + This function is coded in such a way that we will return the + default key cache even if one never called multi_pagecache_init. + This will ensure that it works with old MyISAM clients. + + RETURN + key cache to use +*/ + +PAGECACHE *multi_pagecache_search(byte *key, uint length, + PAGECACHE *def) +{ + if (!pagecache_hash.hash.records) + return def; + return (PAGECACHE*) safe_hash_search(&pagecache_hash, key, length, + (void*) def); +} + + +/* + Assosiate a key cache with a key + + + SYONOPSIS + multi_pagecache_set() + key key (path to table etc..) + length Length of key + pagecache cache to assococite with the table + + NOTES + This can be used both to insert a new entry and change an existing + entry +*/ + + +my_bool multi_pagecache_set(const byte *key, uint length, + PAGECACHE *pagecache) +{ + return safe_hash_set(&pagecache_hash, key, length, (byte*) pagecache); +} + + +void multi_pagecache_change(PAGECACHE *old_data, + PAGECACHE *new_data) +{ + safe_hash_change(&pagecache_hash, (byte*) old_data, (byte*) new_data); +} diff --git a/storage/maria/ma_panic.c b/storage/maria/ma_panic.c index c1312cb1e77..204c3538011 100644 --- a/storage/maria/ma_panic.c +++ b/storage/maria/ma_panic.c @@ -63,7 +63,8 @@ int maria_panic(enum ha_panic_function flag) if (info->s->options & HA_OPTION_READ_ONLY_DATA) break; #endif - if (flush_key_blocks(info->s->key_cache, info->s->kfile, FLUSH_RELEASE)) + if (flush_pagecache_blocks(info->s->pagecache, &info->s->kfile, + FLUSH_RELEASE)) error=my_errno; if (info->opt_flag & WRITE_CACHE_USED) if (flush_io_cache(&info->rec_cache)) @@ -82,29 +83,32 @@ int maria_panic(enum ha_panic_function flag) error=my_errno; } #ifdef CANT_OPEN_FILES_TWICE - if (info->s->kfile >= 0 && my_close(info->s->kfile,MYF(0))) + if (info->s->kfile.file >= 0 && my_close(info->s->kfile.file, MYF(0))) error = my_errno; - if (info->dfile >= 0 && my_close(info->dfile,MYF(0))) + if (info->dfile.file >= 0 && my_close(info->dfile.file, MYF(0))) error = my_errno; - info->s->kfile=info->dfile= -1; /* Files aren't open anymore */ + info->s->kfile.file= info->dfile.file= -1;/* Files aren't open anymore */ break; #endif case HA_PANIC_READ: /* Restore to before WRITE */ #ifdef CANT_OPEN_FILES_TWICE { /* Open closed files */ char name_buff[FN_REFLEN]; - if (info->s->kfile < 0) - if ((info->s->kfile= my_open(fn_format(name_buff,info->filename,"", - N_NAME_IEXT,4),info->mode, - MYF(MY_WME))) < 0) + if (info->s->kfile.file < 0) + if ((info->s->kfile.file= my_open(fn_format(name_buff, + info->filename, "", + N_NAME_IEXT,4), + info->mode, + MYF(MY_WME))) < 0) error = my_errno; - if (info->dfile < 0) + if (info->dfile.file < 0) { - if ((info->dfile= my_open(fn_format(name_buff,info->filename,"", - N_NAME_DEXT,4),info->mode, - MYF(MY_WME))) < 0) + if ((info->dfile.file= my_open(fn_format(name_buff, info->filename, + "", N_NAME_DEXT, 4), + info->mode, + MYF(MY_WME))) < 0) error = my_errno; - info->rec_cache.file=info->dfile; + info->rec_cache.file= info->dfile.file; } } #endif diff --git a/storage/maria/ma_preload.c b/storage/maria/ma_preload.c index f387f2b7de3..5dcfcb35129 100644 --- a/storage/maria/ma_preload.c +++ b/storage/maria/ma_preload.c @@ -69,7 +69,7 @@ int maria_preload(MARIA_HA *info, ulonglong key_map, my_bool ignore_leaves) if (!(buff= (uchar *) my_malloc(length, MYF(MY_WME)))) DBUG_RETURN(my_errno= HA_ERR_OUT_OF_MEM); - if (flush_key_blocks(share->key_cache,share->kfile, FLUSH_RELEASE)) + if (flush_pagecache_blocks(share->pagecache, &share->kfile, FLUSH_RELEASE)) goto err; do @@ -77,7 +77,8 @@ int maria_preload(MARIA_HA *info, ulonglong key_map, my_bool ignore_leaves) /* Read the next block of index file into the preload buffer */ if ((my_off_t) length > (key_file_length-pos)) length= (ulong) (key_file_length-pos); - if (my_pread(share->kfile, (byte*) buff, length, pos, MYF(MY_FAE|MY_FNABP))) + if (my_pread(share->kfile.file, (byte*) buff, length, pos, + MYF(MY_FAE|MY_FNABP))) goto err; if (ignore_leaves) @@ -87,9 +88,15 @@ int maria_preload(MARIA_HA *info, ulonglong key_map, my_bool ignore_leaves) { if (_ma_test_if_nod(buff)) { - if (key_cache_insert(share->key_cache, - share->kfile, pos, DFLT_INIT_HITS, - (byte*) buff, block_length)) + DBUG_ASSERT(share->pagecache->block_size == block_length); + if (pagecache_write(share->pagecache, + &share->kfile, pos / block_length, + DFLT_INIT_HITS, + (byte*) buff, + PAGECACHE_PLAIN_PAGE, + PAGECACHE_LOCK_LEFT_UNLOCKED, + PAGECACHE_PIN_LEFT_PINNED, + PAGECACHE_WRITE_DONE, 0)) goto err; } pos+= block_length; @@ -99,9 +106,14 @@ int maria_preload(MARIA_HA *info, ulonglong key_map, my_bool ignore_leaves) } else { - if (key_cache_insert(share->key_cache, - share->kfile, pos, DFLT_INIT_HITS, - (byte*) buff, length)) + if (pagecache_write(share->pagecache, + &share->kfile, pos / block_length, + DFLT_INIT_HITS, + (byte*) buff, + PAGECACHE_PLAIN_PAGE, + PAGECACHE_LOCK_LEFT_UNLOCKED, + PAGECACHE_PIN_LEFT_PINNED, + PAGECACHE_WRITE_DONE, 0)) goto err; pos+= length; } diff --git a/storage/maria/ma_static.c b/storage/maria/ma_static.c index c5580e1e981..7d5c61d05c8 100644 --- a/storage/maria/ma_static.c +++ b/storage/maria/ma_static.c @@ -41,8 +41,8 @@ my_off_t maria_max_temp_length= MAX_FILE_SIZE; ulong maria_bulk_insert_tree_size=8192*1024; ulong maria_data_pointer_size= 4; -KEY_CACHE maria_key_cache_var; -KEY_CACHE *maria_key_cache= &maria_key_cache_var; +PAGECACHE maria_pagecache_var; +PAGECACHE *maria_pagecache= &maria_pagecache_var; /* Enough for comparing if number is zero */ byte maria_zero_string[]= {0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0}; diff --git a/storage/maria/ma_test1.c b/storage/maria/ma_test1.c index 0f37391c1d4..7f536f71c80 100644 --- a/storage/maria/ma_test1.c +++ b/storage/maria/ma_test1.c @@ -33,7 +33,7 @@ static enum data_file_type record_type= DYNAMIC_RECORD; static uint insert_count, update_count, remove_count; static uint pack_keys=0, pack_seg=0, key_length; static uint unique_key=HA_NOSAME; -static my_bool key_cacheing, null_fields, silent, skip_update, opt_unique, +static my_bool pagecacheing, null_fields, silent, skip_update, opt_unique, verbose, skip_delete; static MARIA_COLUMNDEF recinfo[4]; static MARIA_KEYDEF keyinfo[10]; @@ -51,9 +51,9 @@ int main(int argc,char *argv[]) MY_INIT(argv[0]); my_init(); maria_init(); - if (key_cacheing) - init_key_cache(maria_key_cache,KEY_CACHE_BLOCK_SIZE,IO_SIZE*16,0,0); get_options(argc,argv); + if (pagecacheing) + init_pagecache(maria_pagecache, IO_SIZE*16, 0, 0, MARIA_KEY_BLOCK_LENGTH); exit(run_test("test1")); } @@ -569,8 +569,8 @@ static struct my_option my_long_options[] = 0, 0, 0, GET_NO_ARG, NO_ARG, 0, 0, 0, 0, 0, 0}, {"key-blob", 'b', "Undocumented", 0, 0, 0, GET_NO_ARG, NO_ARG, 0, 0, 0, 0, 0, 0}, - {"key-cache", 'K', "Undocumented", (gptr*) &key_cacheing, - (gptr*) &key_cacheing, 0, GET_BOOL, NO_ARG, 0, 0, 0, 0, 0, 0}, + {"key-cache", 'K', "Undocumented", (gptr*) &pagecacheing, + (gptr*) &pagecacheing, 0, GET_BOOL, NO_ARG, 0, 0, 0, 0, 0, 0}, {"key-length", 'k', "Undocumented", (gptr*) &key_length, (gptr*) &key_length, 0, GET_UINT, REQUIRED_ARG, 6, 0, 0, 0, 0, 0}, {"key-multiple", 'm', "Undocumented", @@ -677,7 +677,7 @@ get_one_option(int optid, const struct my_option *opt __attribute__((unused)), record_type= DYNAMIC_RECORD; break; case 'K': /* Use key cacheing */ - key_cacheing=1; + pagecacheing=1; break; case 'V': printf("test1 Ver 1.2 \n"); diff --git a/storage/maria/ma_test2.c b/storage/maria/ma_test2.c index 46b8c710d4a..a120562bafc 100644 --- a/storage/maria/ma_test2.c +++ b/storage/maria/ma_test2.c @@ -45,13 +45,13 @@ static void copy_key(struct st_maria_info *info,uint inx, uchar *record,uchar *key); static int verbose=0,testflag=0, - first_key=0,async_io=0,key_cacheing=0,write_cacheing=0,locking=0, + first_key=0,async_io=0,pagecacheing=0,write_cacheing=0,locking=0, rec_pointer_size=0,pack_fields=1,silent=0, opt_quick_mode=0; static int pack_seg=HA_SPACE_PACK,pack_type=HA_PACK_KEY,remove_count=-1; static int create_flag= 0, srand_arg= 0; -static ulong key_cache_size=IO_SIZE*16; -static uint key_cache_block_size= KEY_CACHE_BLOCK_SIZE; +static ulong pagecache_size=IO_SIZE*16; +static uint pagecache_block_size= MARIA_KEY_BLOCK_LENGTH; static enum data_file_type record_type= DYNAMIC_RECORD; static uint keys=MARIA_KEYS,recant=1000; @@ -220,8 +220,8 @@ int main(int argc, char *argv[]) goto err; if (!silent) printf("- Writing key:s\n"); - if (key_cacheing) - init_key_cache(maria_key_cache,key_cache_block_size,key_cache_size,0,0); + if (pagecacheing) + init_pagecache(maria_pagecache, pagecache_size, 0, 0, pagecache_block_size); if (locking) maria_lock_database(file,F_WRLCK); if (write_cacheing) @@ -283,9 +283,12 @@ int main(int argc, char *argv[]) goto end; } } - if (key_cacheing) - resize_key_cache(maria_key_cache,key_cache_block_size,key_cache_size*2,0,0); - + /* + TODO: uncomment when resize will be implemented + if (pagecacheing) + resize_pagecache(maria_pagecache, pagecache_block_size, + pagecache_size * 2, 0, 0); + */ if (!silent) printf("- Delete\n"); if (srand_arg) @@ -861,10 +864,10 @@ end: if (rec_pointer_size) printf("Record pointer size: %d\n",rec_pointer_size); printf("maria_block_size: %lu\n", maria_block_size); - if (key_cacheing) + if (pagecacheing) { puts("Key cache used"); - printf("key_cache_block_size: %u\n", key_cache_block_size); + printf("pagecache_block_size: %u\n", pagecache_block_size); if (write_cacheing) puts("Key cache resized"); } @@ -885,14 +888,14 @@ w_requests: %10lu\n\ writes: %10lu\n\ r_requests: %10lu\n\ reads: %10lu\n", - maria_key_cache->blocks_used, - maria_key_cache->global_blocks_changed, - (ulong) maria_key_cache->global_cache_w_requests, - (ulong) maria_key_cache->global_cache_write, - (ulong) maria_key_cache->global_cache_r_requests, - (ulong) maria_key_cache->global_cache_read); + maria_pagecache->blocks_used, + maria_pagecache->global_blocks_changed, + (ulong) maria_pagecache->global_cache_w_requests, + (ulong) maria_pagecache->global_cache_write, + (ulong) maria_pagecache->global_cache_r_requests, + (ulong) maria_pagecache->global_cache_read); } - end_key_cache(maria_key_cache,1); + end_pagecache(maria_pagecache,1); my_free(blob_buffer, MYF(MY_ALLOW_ZERO_PTR)); my_end(silent ? MY_CHECK_ERROR : MY_CHECK_ERROR | MY_GIVE_INFO); return(0); @@ -924,9 +927,9 @@ static void get_options(int argc, char **argv) use_blob= atol(pos); break; case 'K': /* Use key cacheing */ - key_cacheing=1; + pagecacheing=1; if (*++pos) - key_cache_size=atol(pos); + pagecache_size=atol(pos); break; case 'W': /* Use write cacheing */ write_cacheing=1; @@ -968,13 +971,13 @@ static void get_options(int argc, char **argv) maria_block_size= my_round_up_to_next_power(maria_block_size); break; case 'E': /* maria_block_length */ - if ((key_cache_block_size=atoi(++pos)) < MARIA_MIN_KEY_BLOCK_LENGTH || - key_cache_block_size > MARIA_MAX_KEY_BLOCK_LENGTH) + if ((pagecache_block_size=atoi(++pos)) < MARIA_MIN_KEY_BLOCK_LENGTH || + pagecache_block_size > MARIA_MAX_KEY_BLOCK_LENGTH) { - fprintf(stderr,"Wrong key_cache_block_size\n"); + fprintf(stderr,"Wrong pagecache_block_size\n"); exit(1); } - key_cache_block_size= my_round_up_to_next_power(key_cache_block_size); + pagecache_block_size= my_round_up_to_next_power(pagecache_block_size); break; case 'f': if ((first_key=atoi(++pos)) < 0 || first_key >= MARIA_KEYS) diff --git a/storage/maria/ma_test3.c b/storage/maria/ma_test3.c index f6ed248ce16..b784151ad3a 100644 --- a/storage/maria/ma_test3.c +++ b/storage/maria/ma_test3.c @@ -41,7 +41,7 @@ const char *filename= "test3"; -uint tests=10,forks=10,key_cacheing=0; +uint tests=10,forks=10,pagecacheing=0; static void get_options(int argc, char *argv[]); void start_test(int id); @@ -140,10 +140,10 @@ static void get_options(int argc, char **argv) tests=atoi(++pos); break; case 'K': /* Use key cacheing */ - key_cacheing=1; + pagecacheing=1; break; case 'A': /* All flags */ - key_cacheing=1; + pagecacheing=1; break; case '?': case 'I': @@ -178,8 +178,8 @@ void start_test(int id) fprintf(stderr,"Can't open isam-file: %s\n",filename); exit(1); } - if (key_cacheing && rnd(2) == 0) - init_key_cache(maria_key_cache, KEY_CACHE_BLOCK_SIZE, 65536L, 0, 0); + if (pagecacheing && rnd(2) == 0) + init_pagecache(maria_pagecache, 65536L, 0, 0, MARIA_KEY_BLOCK_LENGTH); printf("Process %d, pid: %d\n",id,getpid()); fflush(stdout); for (error=i=0 ; i < tests && !error; i++) diff --git a/storage/maria/ma_write.c b/storage/maria/ma_write.c index 3f1ca59a00a..891f354397c 100644 --- a/storage/maria/ma_write.c +++ b/storage/maria/ma_write.c @@ -69,7 +69,7 @@ int maria_write(MARIA_HA *info, byte *record) my_bool fatal_error; DBUG_ENTER("maria_write"); DBUG_PRINT("enter",("index_file: %d data_file: %d", - info->s->kfile,info->dfile)); + info->s->kfile.file, info->dfile.file)); DBUG_EXECUTE_IF("maria_pretend_crashed_table_on_usage", maria_print_error(info->s, HA_ERR_CRASHED); diff --git a/storage/maria/maria_chk.c b/storage/maria/maria_chk.c index 8471d36bec9..1f0787ef32a 100644 --- a/storage/maria/maria_chk.c +++ b/storage/maria/maria_chk.c @@ -41,7 +41,7 @@ static const char *load_default_groups[]= { "maria_chk", 0 }; static const char *set_collation_name, *opt_tmpdir; static CHARSET_INFO *set_collation; static long opt_maria_block_size; -static long opt_key_cache_block_size; +static long opt_pagecache_block_size; static const char *my_progname_short; static int stopwords_inited= 0; static MY_TMPDIR maria_chk_tmpdir; @@ -302,9 +302,9 @@ static struct my_option my_long_options[] = (gptr*) &check_param.use_buffers, (gptr*) &check_param.use_buffers, 0, GET_ULONG, REQUIRED_ARG, (long) USE_BUFFER_INIT, (long) MALLOC_OVERHEAD, (long) ~0L, (long) MALLOC_OVERHEAD, (long) IO_SIZE, 0}, - { "key_cache_block_size", OPT_KEY_CACHE_BLOCK_SIZE, "", - (gptr*) &opt_key_cache_block_size, - (gptr*) &opt_key_cache_block_size, 0, + { "pagecache_block_size", OPT_KEY_CACHE_BLOCK_SIZE, "", + (gptr*) &opt_pagecache_block_size, + (gptr*) &opt_pagecache_block_size, 0, GET_LONG, REQUIRED_ARG, MARIA_KEY_BLOCK_LENGTH, MARIA_MIN_KEY_BLOCK_LENGTH, MARIA_MAX_KEY_BLOCK_LENGTH, 0, MARIA_MIN_KEY_BLOCK_LENGTH, 0}, { "maria_block_size", OPT_MARIA_BLOCK_SIZE, "", @@ -793,7 +793,7 @@ static void get_options(register int *argc,register char ***argv) exit(1); check_param.tmpdir=&maria_chk_tmpdir; - check_param.key_cache_block_size= opt_key_cache_block_size; + check_param.pagecache_block_size= opt_pagecache_block_size; if (set_collation_name) if (!(set_collation= get_charset_by_name(set_collation_name, @@ -1001,7 +1001,7 @@ static int maria_chk(HA_CHECK *param, my_string filename) use functions that only works on locked tables (like row caching). */ maria_lock_database(info, F_EXTRA_LCK); - datafile=info->dfile; + datafile= info->dfile.file; if (param->testflag & (T_REP_ANY | T_SORT_RECORDS | T_SORT_INDEX)) { @@ -1055,13 +1055,13 @@ static int maria_chk(HA_CHECK *param, my_string filename) #ifndef TO_BE_REMOVED if (param->out_flag & O_NEW_DATA) { /* Change temp file to org file */ - VOID(my_close(info->dfile,MYF(MY_WME))); /* Close new file */ + VOID(my_close(info->dfile.file, MYF(MY_WME))); /* Close new file */ error|=maria_change_to_newfile(filename,MARIA_NAME_DEXT,DATA_TMP_EXT, MYF(0)); if (_ma_open_datafile(info,info->s, -1)) error=1; param->out_flag&= ~O_NEW_DATA; /* We are using new datafile */ - param->read_cache.file=info->dfile; + param->read_cache.file= info->dfile.file; } #endif if (! error) @@ -1080,7 +1080,7 @@ static int maria_chk(HA_CHECK *param, my_string filename) /* what is the following parameter for ? */ (my_bool) !(param->testflag & T_REP), update_index); - datafile=info->dfile; /* This is now locked */ + datafile= info->dfile.file; /* This is now locked */ if (!error && !update_index) { if (param->verbose) @@ -1125,8 +1125,8 @@ static int maria_chk(HA_CHECK *param, my_string filename) !(param->testflag & (T_FAST | T_FORCE_CREATE))) { if (param->testflag & (T_EXTEND | T_MEDIUM)) - VOID(init_key_cache(maria_key_cache,opt_key_cache_block_size, - param->use_buffers, 0, 0)); + VOID(init_pagecache(maria_pagecache, param->use_buffers, 0, 0, + opt_pagecache_block_size)); VOID(init_io_cache(¶m->read_cache,datafile, (uint) param->read_buffer_length, READ_CACHE, @@ -1139,7 +1139,7 @@ static int maria_chk(HA_CHECK *param, my_string filename) if ((info->s->data_file_type != STATIC_RECORD) || (param->testflag & (T_EXTEND | T_MEDIUM))) error|=maria_chk_data_link(param, info, param->testflag & T_EXTEND); - error|=_ma_flush_blocks(param, share->key_cache, share->kfile); + error|=_ma_flush_blocks(param, share->pagecache, &share->kfile); VOID(end_io_cache(¶m->read_cache)); } if (!error) @@ -1534,8 +1534,8 @@ static int maria_sort_records(HA_CHECK *param, if (share->state.key_root[sort_key] == HA_OFFSET_ERROR) DBUG_RETURN(0); /* Nothing to do */ - init_key_cache(maria_key_cache, opt_key_cache_block_size, param->use_buffers, - 0, 0); + init_pagecache(maria_pagecache, param->use_buffers, + 0, 0, opt_pagecache_block_size); if (init_io_cache(&info->rec_cache,-1,(uint) param->write_buffer_length, WRITE_CACHE,share->pack.header_length,1, MYF(MY_WME | MY_WAIT_IF_FULL))) @@ -1566,8 +1566,9 @@ static int maria_sort_records(HA_CHECK *param, goto err; } if (share->pack.header_length) - if (maria_filecopy(param,new_file,info->dfile,0L,share->pack.header_length, - "datafile-header")) + if (maria_filecopy(param, new_file, info->dfile.file, 0L, + share->pack.header_length, + "datafile-header")) goto err; info->rec_cache.file=new_file; /* Use this file for cacheing*/ @@ -1575,7 +1576,7 @@ static int maria_sort_records(HA_CHECK *param, for (key=0 ; key < share->base.keys ; key++) share->keyinfo[key].flag|= HA_SORT_ALLOWS_SAME; - if (my_pread(share->kfile, temp_buff, + if (my_pread(share->kfile.file, temp_buff, (uint) keyinfo->block_length, share->state.key_root[sort_key], MYF(MY_NABP+MY_WME))) @@ -1611,9 +1612,9 @@ static int maria_sort_records(HA_CHECK *param, goto err; } - VOID(my_close(info->dfile,MYF(MY_WME))); + VOID(my_close(info->dfile.file, MYF(MY_WME))); param->out_flag|=O_NEW_DATA; /* Data in new file */ - info->dfile=new_file; /* Use new datafile */ + info->dfile.file= new_file; /* Use new datafile */ info->state->del=0; info->state->empty=0; share->state.dellink= HA_OFFSET_ERROR; @@ -1646,7 +1647,7 @@ err: my_free(sort_info.buff,MYF(MY_ALLOW_ZERO_PTR)); sort_info.buff=0; share->state.sortkey=sort_key; - DBUG_RETURN(_ma_flush_blocks(param, share->key_cache, share->kfile) | + DBUG_RETURN(_ma_flush_blocks(param, share->pagecache, &share->kfile) | got_error); } /* sort_records */ @@ -1687,7 +1688,7 @@ static int sort_record_index(MARIA_SORT_PARAM *sort_param,MARIA_HA *info, if (nod_flag) { next_page= _ma_kpos(nod_flag, keypos); - if (my_pread(info->s->kfile,(byte*) temp_buff, + if (my_pread(info->s->kfile.file, (byte*)temp_buff, (uint) keyinfo->block_length, next_page, MYF(MY_NABP+MY_WME))) { @@ -1728,7 +1729,7 @@ static int sort_record_index(MARIA_SORT_PARAM *sort_param,MARIA_HA *info, } /* Clear end of block to get better compression if the table is backuped */ bzero((byte*) buff+used_length,keyinfo->block_length-used_length); - if (my_pwrite(info->s->kfile,(byte*) buff,(uint) keyinfo->block_length, + if (my_pwrite(info->s->kfile.file, (byte*)buff, (uint)keyinfo->block_length, page,param->myf_rw)) { _ma_check_print_error(param,"%d when updating keyblock",my_errno); diff --git a/storage/maria/maria_def.h b/storage/maria/maria_def.h index b174df2fa3e..2d11dd07900 100644 --- a/storage/maria/maria_def.h +++ b/storage/maria/maria_def.h @@ -176,10 +176,10 @@ typedef struct st_maria_pack typedef struct st_maria_file_bitmap { + File file; /* should be first for compatibility with PAGECACHE_FILE */ uchar *map; ulonglong page; /* Page number for current bitmap */ uint used_size; /* Size of bitmap that is not 0 */ - File file; my_bool changed; @@ -214,7 +214,7 @@ typedef struct st_maria_share symlinks */ *index_file_name; byte *file_map; /* mem-map of file if possible */ - KEY_CACHE *key_cache; /* ref to the current key cache */ + PAGECACHE *pagecache; /* ref to the current key cache */ MARIA_DECODE_TREE *decode_trees; uint16 *decode_tables; my_bool (*once_init)(struct st_maria_share *, File); @@ -250,7 +250,7 @@ typedef struct st_maria_share uint unique_name_length; uint32 ftparsers; /* Number of distinct ftparsers + 1 */ - File kfile; /* Shared keyfile */ + PAGECACHE_FILE kfile; /* Shared keyfile */ File data_file; /* Shared data file */ int mode; /* mode of file on open */ uint reopen; /* How many times reopened */ @@ -381,7 +381,7 @@ struct st_maria_info */ ulong packed_length, blob_length; /* Length of found, packed record */ my_size_t rec_buff_size; - int dfile; /* The datafile */ + PAGECACHE_FILE dfile; /* The datafile */ uint opt_flag; /* Optim. for space/speed */ uint update; /* If file changed since open */ int lastinx; /* Last used index */ @@ -845,7 +845,8 @@ int _ma_thr_write_keys(MARIA_SORT_PARAM *sort_param); #ifdef THREAD pthread_handler_t _ma_thr_find_all_keys(void *arg); #endif -int _ma_flush_blocks(HA_CHECK *param, KEY_CACHE *key_cache, File file); +int _ma_flush_blocks(HA_CHECK *param, PAGECACHE *pagecache, + PAGECACHE_FILE *file); int _ma_sort_write_record(MARIA_SORT_PARAM *sort_param); int _ma_create_index_by_sort(MARIA_SORT_PARAM *info, my_bool no_messages, diff --git a/storage/maria/maria_ftdump.c b/storage/maria/maria_ftdump.c index ef30540bfce..fecbe7575c8 100644 --- a/storage/maria/maria_ftdump.c +++ b/storage/maria/maria_ftdump.c @@ -85,7 +85,8 @@ int main(int argc,char *argv[]) usage(); } - init_key_cache(maria_key_cache,MARIA_KEY_BLOCK_LENGTH,USE_BUFFER_INIT, 0, 0); + init_pagecache(maria_pagecache, USE_BUFFER_INIT, 0, 0, + MARIA_KEY_BLOCK_LENGTH); if (!(info=maria_open(argv[0], O_RDONLY, HA_OPEN_ABORT_IF_LOCKED|HA_OPEN_FROM_SQL_LAYER))) diff --git a/storage/maria/maria_pack.c b/storage/maria/maria_pack.c index 41c519693d5..57d5956f38e 100644 --- a/storage/maria/maria_pack.c +++ b/storage/maria/maria_pack.c @@ -525,7 +525,7 @@ static int compress(PACK_MRG_INFO *mrg,char *result_table) length=(uint) share->base.keystart; if (!(buff=my_malloc(length,MYF(MY_WME)))) goto err; - if (my_pread(share->kfile,buff,length,0L,MYF(MY_WME | MY_NABP)) || + if (my_pread(share->kfile.file, buff, length, 0L, MYF(MY_WME | MY_NABP)) || my_write(join_isam_file,buff,length, MYF(MY_WME | MY_NABP | MY_WAIT_IF_FULL))) { @@ -679,8 +679,8 @@ static int compress(PACK_MRG_INFO *mrg,char *result_table) error|=my_close(new_file,MYF(MY_WME)); if (!result_table) { - error|=my_close(isam_file->dfile,MYF(MY_WME)); - isam_file->dfile= -1; /* Tell maria_close file is closed */ + error|=my_close(isam_file->dfile.file, MYF(MY_WME)); + isam_file->dfile.file= -1; /* Tell maria_close file is closed */ isam_file->s->bitmap.file= -1; } } @@ -2983,10 +2983,10 @@ static int save_state(MARIA_HA *isam_file,PACK_MRG_INFO *mrg, share->changed=1; /* Force write of header */ share->state.open_count=0; share->global_changed=0; - VOID(my_chsize(share->kfile, share->base.keystart, 0, MYF(0))); + VOID(my_chsize(share->kfile.file, share->base.keystart, 0, MYF(0))); if (share->base.keys) isamchk_neaded=1; - DBUG_RETURN(_ma_state_info_write(share->kfile,&share->state,1+2)); + DBUG_RETURN(_ma_state_info_write(share->kfile.file, &share->state, (1 + 2))); } diff --git a/storage/maria/unittest/Makefile.am b/storage/maria/unittest/Makefile.am index 33f1bfed560..76c8aa24779 100644 --- a/storage/maria/unittest/Makefile.am +++ b/storage/maria/unittest/Makefile.am @@ -26,19 +26,18 @@ LDADD= $(top_builddir)/unittest/mytap/libmytap.a \ $(top_builddir)/storage/myisam/libmyisam.a \ $(top_builddir)/mysys/libmysys.a \ $(top_builddir)/dbug/libdbug.a \ - $(top_builddir)/strings/libmystrings.a @ZLIB_LIBS@ \ - $(top_builddir)/storage/maria/ma_loghandler.o + $(top_builddir)/strings/libmystrings.a @ZLIB_LIBS@ noinst_PROGRAMS = ma_control_file-t trnman-t lockman2-t \ - mf_pagecache_single_1k-t mf_pagecache_single_8k-t \ - mf_pagecache_single_64k-t-big \ - mf_pagecache_consist_1k-t-big \ - mf_pagecache_consist_64k-t-big \ - mf_pagecache_consist_1kHC-t-big \ - mf_pagecache_consist_64kHC-t-big \ - mf_pagecache_consist_1kRD-t-big \ - mf_pagecache_consist_64kRD-t-big \ - mf_pagecache_consist_1kWR-t-big \ - mf_pagecache_consist_64kWR-t-big \ + ma_pagecache_single_1k-t ma_pagecache_single_8k-t \ + ma_pagecache_single_64k-t-big \ + ma_pagecache_consist_1k-t-big \ + ma_pagecache_consist_64k-t-big \ + ma_pagecache_consist_1kHC-t-big \ + ma_pagecache_consist_64kHC-t-big \ + ma_pagecache_consist_1kRD-t-big \ + ma_pagecache_consist_64kRD-t-big \ + ma_pagecache_consist_1kWR-t-big \ + ma_pagecache_consist_64kWR-t-big \ ma_test_loghandler-t \ ma_test_loghandler_multigroup-t \ ma_test_loghandler_multithread-t \ @@ -49,36 +48,36 @@ ma_test_loghandler_multigroup_t_SOURCES= ma_test_loghandler_multigroup-t.c ma_ma ma_test_loghandler_multithread_t_SOURCES= ma_test_loghandler_multithread-t.c ma_maria_log_cleanup.c ma_test_loghandler_pagecache_t_SOURCES= ma_test_loghandler_pagecache-t.c ma_maria_log_cleanup.c -mf_pagecache_single_src = mf_pagecache_single.c $(top_srcdir)/mysys/mf_pagecache.c test_file.c -mf_pagecache_consist_src = mf_pagecache_consist.c $(top_srcdir)/mysys/mf_pagecache.c test_file.c -mf_pagecache_common_cppflags = -DEXTRA_DEBUG -DPAGECACHE_DEBUG -DMAIN +ma_pagecache_single_src = ma_pagecache_single.c test_file.c +ma_pagecache_consist_src = ma_pagecache_consist.c test_file.c +ma_pagecache_common_cppflags = -DEXTRA_DEBUG -DPAGECACHE_DEBUG -DMAIN -mf_pagecache_single_1k_t_SOURCES = $(mf_pagecache_single_src) -mf_pagecache_single_8k_t_SOURCES = $(mf_pagecache_single_src) -mf_pagecache_single_64k_t_big_SOURCES = $(mf_pagecache_single_src) -mf_pagecache_single_1k_t_CPPFLAGS = $(mf_pagecache_common_cppflags) -DPAGE_SIZE=1024 -mf_pagecache_single_8k_t_CPPFLAGS = $(mf_pagecache_common_cppflags) -DPAGE_SIZE=8192 -mf_pagecache_single_64k_t_big_CPPFLAGS = $(mf_pagecache_common_cppflags) -DPAGE_SIZE=65536 +ma_pagecache_single_1k_t_SOURCES = $(ma_pagecache_single_src) +ma_pagecache_single_8k_t_SOURCES = $(ma_pagecache_single_src) +ma_pagecache_single_64k_t_big_SOURCES = $(ma_pagecache_single_src) +ma_pagecache_single_1k_t_CPPFLAGS = $(ma_pagecache_common_cppflags) -DPAGE_SIZE=1024 +ma_pagecache_single_8k_t_CPPFLAGS = $(ma_pagecache_common_cppflags) -DPAGE_SIZE=8192 +ma_pagecache_single_64k_t_big_CPPFLAGS = $(ma_pagecache_common_cppflags) -DPAGE_SIZE=65536 -mf_pagecache_consist_1k_t_big_SOURCES = $(mf_pagecache_consist_src) -mf_pagecache_consist_1k_t_big_CPPFLAGS = $(mf_pagecache_common_cppflags) -DPAGE_SIZE=1024 -mf_pagecache_consist_64k_t_big_SOURCES = $(mf_pagecache_consist_src) -mf_pagecache_consist_64k_t_big_CPPFLAGS = $(mf_pagecache_common_cppflags) -DPAGE_SIZE=65536 +ma_pagecache_consist_1k_t_big_SOURCES = $(ma_pagecache_consist_src) +ma_pagecache_consist_1k_t_big_CPPFLAGS = $(ma_pagecache_common_cppflags) -DPAGE_SIZE=1024 +ma_pagecache_consist_64k_t_big_SOURCES = $(ma_pagecache_consist_src) +ma_pagecache_consist_64k_t_big_CPPFLAGS = $(ma_pagecache_common_cppflags) -DPAGE_SIZE=65536 -mf_pagecache_consist_1kHC_t_big_SOURCES = $(mf_pagecache_consist_src) -mf_pagecache_consist_1kHC_t_big_CPPFLAGS = $(mf_pagecache_common_cppflags) -DPAGE_SIZE=1024 -DTEST_HIGH_CONCURENCY -mf_pagecache_consist_64kHC_t_big_SOURCES = $(mf_pagecache_consist_src) -mf_pagecache_consist_64kHC_t_big_CPPFLAGS = $(mf_pagecache_common_cppflags) -DPAGE_SIZE=65536 -DTEST_HIGH_CONCURENCY +ma_pagecache_consist_1kHC_t_big_SOURCES = $(ma_pagecache_consist_src) +ma_pagecache_consist_1kHC_t_big_CPPFLAGS = $(ma_pagecache_common_cppflags) -DPAGE_SIZE=1024 -DTEST_HIGH_CONCURENCY +ma_pagecache_consist_64kHC_t_big_SOURCES = $(ma_pagecache_consist_src) +ma_pagecache_consist_64kHC_t_big_CPPFLAGS = $(ma_pagecache_common_cppflags) -DPAGE_SIZE=65536 -DTEST_HIGH_CONCURENCY -mf_pagecache_consist_1kRD_t_big_SOURCES = $(mf_pagecache_consist_src) -mf_pagecache_consist_1kRD_t_big_CPPFLAGS = $(mf_pagecache_common_cppflags) -DPAGE_SIZE=1024 -DTEST_READERS -mf_pagecache_consist_64kRD_t_big_SOURCES = $(mf_pagecache_consist_src) -mf_pagecache_consist_64kRD_t_big_CPPFLAGS = $(mf_pagecache_common_cppflags) -DPAGE_SIZE=65536 -DTEST_READERS +ma_pagecache_consist_1kRD_t_big_SOURCES = $(ma_pagecache_consist_src) +ma_pagecache_consist_1kRD_t_big_CPPFLAGS = $(ma_pagecache_common_cppflags) -DPAGE_SIZE=1024 -DTEST_READERS +ma_pagecache_consist_64kRD_t_big_SOURCES = $(ma_pagecache_consist_src) +ma_pagecache_consist_64kRD_t_big_CPPFLAGS = $(ma_pagecache_common_cppflags) -DPAGE_SIZE=65536 -DTEST_READERS -mf_pagecache_consist_1kWR_t_big_SOURCES = $(mf_pagecache_consist_src) -mf_pagecache_consist_1kWR_t_big_CPPFLAGS = $(mf_pagecache_common_cppflags) -DPAGE_SIZE=1024 -DTEST_WRITERS -mf_pagecache_consist_64kWR_t_big_SOURCES = $(mf_pagecache_consist_src) -mf_pagecache_consist_64kWR_t_big_CPPFLAGS = $(mf_pagecache_common_cppflags) -DPAGE_SIZE=65536 -DTEST_WRITERS +ma_pagecache_consist_1kWR_t_big_SOURCES = $(ma_pagecache_consist_src) +ma_pagecache_consist_1kWR_t_big_CPPFLAGS = $(ma_pagecache_common_cppflags) -DPAGE_SIZE=1024 -DTEST_WRITERS +ma_pagecache_consist_64kWR_t_big_SOURCES = $(ma_pagecache_consist_src) +ma_pagecache_consist_64kWR_t_big_CPPFLAGS = $(ma_pagecache_common_cppflags) -DPAGE_SIZE=65536 -DTEST_WRITERS # the generic lock manager may not be used in the end and lockman1-t crashes, # so we don't build lockman-t and lockman1-t diff --git a/storage/maria/unittest/mf_pagecache_consist.c b/storage/maria/unittest/ma_pagecache_consist.c index 8ea0094762c..3346160429d 100755 --- a/storage/maria/unittest/mf_pagecache_consist.c +++ b/storage/maria/unittest/ma_pagecache_consist.c @@ -97,7 +97,7 @@ uint check_page(uchar *buff, ulong offset, int page_locked, int page_no, end+= sizeof(uint) + sizeof(uint); if (len + end > PAGE_SIZE) { - diag("incorrect field header #%u by offset %lu\n", i, offset + end + j); + diag("incorrect field header #%u by offset %lu\n", i, offset + end); goto err; } for(j= 0; j < len; j++) diff --git a/storage/maria/unittest/mf_pagecache_single.c b/storage/maria/unittest/ma_pagecache_single.c index 91cceee618d..91cceee618d 100644 --- a/storage/maria/unittest/mf_pagecache_single.c +++ b/storage/maria/unittest/ma_pagecache_single.c |