diff options
author | shennetsind <ind@henn.et> | 2014-01-12 13:27:53 -0200 |
---|---|---|
committer | shennetsind <ind@henn.et> | 2014-01-12 13:27:53 -0200 |
commit | 209d15e07d52a52c110b01f4bad0b52080a69550 (patch) | |
tree | 25323e678f26f09143b7c3c486f5f81ac6379e7f | |
parent | 95f13f3420822111f928ba6079fbc2061bd38c5f (diff) | |
download | hercules-209d15e07d52a52c110b01f4bad0b52080a69550.tar.gz hercules-209d15e07d52a52c110b01f4bad0b52080a69550.tar.bz2 hercules-209d15e07d52a52c110b01f4bad0b52080a69550.tar.xz hercules-209d15e07d52a52c110b01f4bad0b52080a69550.zip |
Fixed ERS Cache sharing
Enforcing cache to match the option condition in order for it to be shared. Special Thanks to Haruna!
Signed-off-by: shennetsind <ind@henn.et>
-rw-r--r-- | src/common/db.c | 5 | ||||
-rw-r--r-- | src/common/ers.c | 25 | ||||
-rw-r--r-- | src/common/ers.h | 4 | ||||
-rw-r--r-- | src/map/map.c | 7 | ||||
-rw-r--r-- | src/map/pc.c | 6 | ||||
-rw-r--r-- | src/map/script.c | 4 | ||||
-rw-r--r-- | src/map/skill.c | 10 |
7 files changed, 39 insertions, 22 deletions
diff --git a/src/common/db.c b/src/common/db.c index ddfb032d4..8c15c0feb 100644 --- a/src/common/db.c +++ b/src/common/db.c @@ -2751,9 +2751,10 @@ void* db_data2ptr(DBData *data) * @see #db_final(void) */ void db_init(void) { - db_iterator_ers = ers_new(sizeof(struct DBIterator_impl),"db.c::db_iterator_ers",ERS_OPT_CLEAN); - db_alloc_ers = ers_new(sizeof(struct DBMap_impl),"db.c::db_alloc_ers",ERS_OPT_CLEAN); + db_iterator_ers = ers_new(sizeof(struct DBIterator_impl),"db.c::db_iterator_ers",ERS_OPT_CLEAN|ERS_OPT_FLEX_CHUNK); + db_alloc_ers = ers_new(sizeof(struct DBMap_impl),"db.c::db_alloc_ers",ERS_OPT_CLEAN|ERS_OPT_FLEX_CHUNK); ers_chunk_size(db_alloc_ers, 50); + ers_chunk_size(db_iterator_ers, 10); DB_COUNTSTAT(db_init); } diff --git a/src/common/ers.c b/src/common/ers.c index a7dad49ab..eb351a988 100644 --- a/src/common/ers.c +++ b/src/common/ers.c @@ -45,6 +45,7 @@ #include "../common/cbasetypes.h" #include "../common/malloc.h" // CREATE, RECREATE, aMalloc, aFree #include "../common/showmsg.h" // ShowMessage, ShowError, ShowFatalError, CL_BOLD, CL_NORMAL +#include "../common/nullpo.h" #include "ers.h" #ifndef DISABLE_ERS @@ -88,6 +89,9 @@ typedef struct ers_cache // Default = ERS_BLOCK_ENTRIES, can be adjusted for performance for individual cache sizes. unsigned int ChunkSize; + // Misc options, some options are shared from the instance + enum ERSOptions Options; + // Linked list struct ers_cache *Next, *Prev; } ers_cache_t; @@ -123,12 +127,14 @@ static ers_cache_t *CacheList = NULL; static struct ers_instance_t *InstanceList = NULL; #endif -static ers_cache_t *ers_find_cache(unsigned int size) -{ +/** + * @param Options the options from the instance seeking a cache, we use it to give it a cache with matching configuration + **/ +static ers_cache_t *ers_find_cache(unsigned int size, enum ERSOptions Options) { ers_cache_t *cache; for (cache = CacheList; cache; cache = cache->Next) - if (cache->ObjectSize == size) + if ( cache->ObjectSize == size && cache->Options == ( Options & ERS_CACHE_OPTIONS ) ) return cache; CREATE(cache, ers_cache_t, 1); @@ -141,6 +147,7 @@ static ers_cache_t *ers_find_cache(unsigned int size) cache->UsedObjs = 0; cache->Max = 0; cache->ChunkSize = ERS_BLOCK_ENTRIES; + cache->Options = (Options & ERS_CACHE_OPTIONS); if (CacheList == NULL) { @@ -239,7 +246,7 @@ static void ers_obj_free_entry(ERS self, void *entry) return; } - if( instance->Options & ERS_OPT_CLEAN ) + if( instance->Cache->Options & ERS_OPT_CLEAN ) memset((unsigned char*)reuse + sizeof(struct ers_list), 0, instance->Cache->ObjectSize - sizeof(struct ers_list)); reuse->Next = instance->Cache->ReuseList; @@ -297,9 +304,10 @@ static void ers_obj_destroy(ERS self) void ers_cache_size(ERS self, unsigned int new_size) { struct ers_instance_t *instance = (struct ers_instance_t *)self; - if (instance == NULL) {//change as per piotrhalaczkiewicz comment - ShowError("ers_cache_size: NULL object, skipping...\n"); - return; + nullpo_retv(instance); + + if( !(instance->Cache->Options&ERS_OPT_FLEX_CHUNK) ) { + ShowWarning("ers_cache_size: '%s' has adjusted its chunk size to '%d', however ERS_OPT_FLEX_CHUNK is missing!\n",instance->Name,new_size); } instance->Cache->ChunkSize = new_size; @@ -324,7 +332,8 @@ ERS ers_new(uint32 size, char *name, enum ERSOptions options) instance->Name = ( options & ERS_OPT_FREE_NAME ) ? aStrdup(name) : name; instance->Options = options; - instance->Cache = ers_find_cache(size); + instance->Cache = ers_find_cache(size,instance->Options); + instance->Cache->ReferenceCount++; #ifdef DEBUG if (InstanceList == NULL) { diff --git a/src/common/ers.h b/src/common/ers.h index e63711b81..d74ee02a5 100644 --- a/src/common/ers.h +++ b/src/common/ers.h @@ -76,6 +76,10 @@ enum ERSOptions { ERS_OPT_WAIT = 0x2,/* wait for entries to come in order to list! */ ERS_OPT_FREE_NAME = 0x4,/* name is dynamic memory, and should be freed */ ERS_OPT_CLEAN = 0x8,/* clears used memory upon ers_free so that its all new to be reused on the next alloc */ + ERS_OPT_FLEX_CHUNK = 0x10,/* signs that it should look for its own cache given it'll have a dynamic chunk size, so that it doesn't affect the other ERS it'd otherwise be sharing */ + + /* Compound, is used to determine whether it should be looking for a cache of matching options */ + ERS_CACHE_OPTIONS = ERS_OPT_CLEAN|ERS_OPT_FLEX_CHUNK, }; /** diff --git a/src/map/map.c b/src/map/map.c index 922807158..68a675a37 100644 --- a/src/map/map.c +++ b/src/map/map.c @@ -5558,9 +5558,10 @@ int do_init(int argc, char *argv[]) map->iwall_db = strdb_alloc(DB_OPT_RELEASE_DATA,2*NAME_LENGTH+2+1); // [Zephyrus] Invisible Walls map->zone_db = strdb_alloc(DB_OPT_DUP_KEY|DB_OPT_RELEASE_DATA, MAP_ZONE_NAME_LENGTH); - map->iterator_ers = ers_new(sizeof(struct s_mapiterator),"map.c::map_iterator_ers",ERS_OPT_CLEAN); - - map->flooritem_ers = ers_new(sizeof(struct flooritem_data),"map.c::map_flooritem_ers",ERS_OPT_CLEAN); + map->iterator_ers = ers_new(sizeof(struct s_mapiterator),"map.c::map_iterator_ers",ERS_OPT_CLEAN|ERS_OPT_FLEX_CHUNK); + ers_chunk_size(map->iterator_ers, 25); + + map->flooritem_ers = ers_new(sizeof(struct flooritem_data),"map.c::map_flooritem_ers",ERS_OPT_CLEAN|ERS_OPT_FLEX_CHUNK); ers_chunk_size(map->flooritem_ers, 100); if (!minimal) { diff --git a/src/map/pc.c b/src/map/pc.c index b090b7b17..e6ad4e20c 100644 --- a/src/map/pc.c +++ b/src/map/pc.c @@ -10513,9 +10513,9 @@ void do_init_pc(bool minimal) { pcg->init(); - pc->sc_display_ers = ers_new(sizeof(struct sc_display_entry), "pc.c:sc_display_ers", ERS_OPT_NONE); - pc->num_reg_ers = ers_new(sizeof(struct script_reg_num), "pc.c::num_reg_ers", ERS_OPT_CLEAN); - pc->str_reg_ers = ers_new(sizeof(struct script_reg_str), "pc.c::str_reg_ers", ERS_OPT_CLEAN); + pc->sc_display_ers = ers_new(sizeof(struct sc_display_entry), "pc.c:sc_display_ers", ERS_OPT_FLEX_CHUNK); + pc->num_reg_ers = ers_new(sizeof(struct script_reg_num), "pc.c::num_reg_ers", ERS_OPT_CLEAN|ERS_OPT_FLEX_CHUNK); + pc->str_reg_ers = ers_new(sizeof(struct script_reg_str), "pc.c::str_reg_ers", ERS_OPT_CLEAN|ERS_OPT_FLEX_CHUNK); ers_chunk_size(pc->sc_display_ers, 150); ers_chunk_size(pc->num_reg_ers, 300); diff --git a/src/map/script.c b/src/map/script.c index 76cb2ef89..a55b43791 100644 --- a/src/map/script.c +++ b/src/map/script.c @@ -4302,8 +4302,8 @@ void do_init_script(bool minimal) { script->userfunc_db = strdb_alloc(DB_OPT_DUP_KEY,0); script->autobonus_db = strdb_alloc(DB_OPT_DUP_KEY,0); - script->st_ers = ers_new(sizeof(struct script_state), "script.c::st_ers", ERS_OPT_CLEAN); - script->stack_ers = ers_new(sizeof(struct script_stack), "script.c::script_stack", ERS_OPT_NONE); + script->st_ers = ers_new(sizeof(struct script_state), "script.c::st_ers", ERS_OPT_CLEAN|ERS_OPT_FLEX_CHUNK); + script->stack_ers = ers_new(sizeof(struct script_stack), "script.c::script_stack", ERS_OPT_NONE|ERS_OPT_FLEX_CHUNK); script->array_ers = ers_new(sizeof(struct script_array), "script.c::array_ers", ERS_OPT_CLEAN|ERS_OPT_CLEAR); ers_chunk_size(script->st_ers, 10); diff --git a/src/map/skill.c b/src/map/skill.c index 0804adf90..0df90a538 100644 --- a/src/map/skill.c +++ b/src/map/skill.c @@ -18202,13 +18202,15 @@ int do_init_skill(bool minimal) { skill->cd_db = idb_alloc(DB_OPT_BASE); skill->usave_db = idb_alloc(DB_OPT_RELEASE_DATA); - skill->unit_ers = ers_new(sizeof(struct skill_unit_group),"skill.c::skill_unit_ers",ERS_OPT_CLEAN); - skill->timer_ers = ers_new(sizeof(struct skill_timerskill),"skill.c::skill_timer_ers",ERS_OPT_NONE); - skill->cd_ers = ers_new(sizeof(struct skill_cd),"skill.c::skill_cd_ers",ERS_OPT_CLEAR|ERS_OPT_CLEAN); - skill->cd_entry_ers = ers_new(sizeof(struct skill_cd_entry),"skill.c::skill_cd_entry_ers",ERS_OPT_CLEAR); + skill->unit_ers = ers_new(sizeof(struct skill_unit_group),"skill.c::skill_unit_ers",ERS_OPT_CLEAN|ERS_OPT_FLEX_CHUNK); + skill->timer_ers = ers_new(sizeof(struct skill_timerskill),"skill.c::skill_timer_ers",ERS_OPT_NONE|ERS_OPT_FLEX_CHUNK); + skill->cd_ers = ers_new(sizeof(struct skill_cd),"skill.c::skill_cd_ers",ERS_OPT_CLEAR|ERS_OPT_CLEAN|ERS_OPT_FLEX_CHUNK); + skill->cd_entry_ers = ers_new(sizeof(struct skill_cd_entry),"skill.c::skill_cd_entry_ers",ERS_OPT_CLEAR|ERS_OPT_FLEX_CHUNK); ers_chunk_size(skill->cd_ers, 25); ers_chunk_size(skill->cd_entry_ers, 100); + ers_chunk_size(skill->unit_ers, 150); + ers_chunk_size(skill->timer_ers, 150); timer->add_func_list(skill->unit_timer,"skill_unit_timer"); timer->add_func_list(skill->castend_id,"skill_castend_id"); |