From e47f40af9e89b3261b1b0da261fc7d1a1b2b2927 Mon Sep 17 00:00:00 2001 From: MysterD Date: Mon, 27 Mar 2023 14:29:15 -0700 Subject: [PATCH] Swapped out hashmap to C++ for sync objects --- data/dynos_cmap.cpp | 74 ++++++++++++++++++++++++++++ data/dynos_cmap.cpp.h | 17 +++++++ src/pc/lua/smlua_cobject_allowlist.c | 1 + src/pc/network/sync_object.c | 40 ++++++--------- src/pc/network/sync_object.h | 1 + src/pc/pc_main.c | 1 + 6 files changed, 109 insertions(+), 25 deletions(-) create mode 100644 data/dynos_cmap.cpp create mode 100644 data/dynos_cmap.cpp.h diff --git a/data/dynos_cmap.cpp b/data/dynos_cmap.cpp new file mode 100644 index 00000000..02680cbc --- /dev/null +++ b/data/dynos_cmap.cpp @@ -0,0 +1,74 @@ +#include + +typedef std::map Map; + +struct MapIter { + Map* map; + Map::iterator itr; +}; + +extern "C" { + +void* hmap_create() { + return reinterpret_cast (new Map()); +} + +void* hmap_get(void* map, int64_t k) { + Map* m = reinterpret_cast (map); + Map::iterator pos = m->find(k); + if (pos == m->end()) { + return NULL; + } else { + return pos->second; + } +} + +void hmap_put(void* map, int64_t k, void* v) { + Map* m = reinterpret_cast (map); + if (m->count(k) > 0) { + m->erase(k); + } + m->insert(std::pair(k, v)); +} + +void hmap_del(void* map, int64_t k) { + Map* m = reinterpret_cast (map); + m->erase(k); +} + +void hmap_clear(void* map) { + Map* m = reinterpret_cast (map); + m->clear(); +} + +size_t hmap_len(void* map) { + Map* m = reinterpret_cast (map); + return m->size(); +} + +void* hmap_iter(void* map) { + auto iter = new MapIter(); + Map* m = reinterpret_cast (map); + iter->map = m; + return reinterpret_cast (iter); +} + +void* hmap_begin(void* iter) { + MapIter* i = reinterpret_cast (iter); + i->itr = i->map->begin(); + if (i->itr == i->map->end()) { + return NULL; + } + return i->itr->second; +} + +void* hmap_next(void* iter) { + MapIter* i = reinterpret_cast (iter); + i->itr++; + if (i->itr == i->map->end()) { + return NULL; + } + return i->itr->second; +} + +} // extern "C" \ No newline at end of file diff --git a/data/dynos_cmap.cpp.h b/data/dynos_cmap.cpp.h new file mode 100644 index 00000000..77c7c7f7 --- /dev/null +++ b/data/dynos_cmap.cpp.h @@ -0,0 +1,17 @@ +#ifndef DYNOS_CMAP_CPP_H +#define DYNOS_CMAP_CPP_H +#ifndef __cplusplus + +void* hmap_create(); +void* hmap_get(void* map, int64_t k); +void hmap_put(void* map, int64_t k, void* v); +void hmap_del(void* map, int64_t k); +void hmap_clear(void* map); +size_t hmap_len(void* map); + +void* hmap_iter(void* map); +void* hmap_begin(void* iter); +void* hmap_next(void* iter); + +#endif +#endif \ No newline at end of file diff --git a/src/pc/lua/smlua_cobject_allowlist.c b/src/pc/lua/smlua_cobject_allowlist.c index ecd6a166..e1631b9d 100644 --- a/src/pc/lua/smlua_cobject_allowlist.c +++ b/src/pc/lua/smlua_cobject_allowlist.c @@ -1,5 +1,6 @@ #include #include "smlua.h" +#define STB_DS_IMPLEMENTATION 1 #include "pc/utils/stb_ds.h" struct AllowList { diff --git a/src/pc/network/sync_object.c b/src/pc/network/sync_object.c index 343c539f..7aee05f9 100644 --- a/src/pc/network/sync_object.c +++ b/src/pc/network/sync_object.c @@ -10,15 +10,10 @@ #include "game/object_helpers.h" #include "pc/debuglog.h" #include "pc/utils/misc.h" +#include "data/dynos_cmap.cpp.h" -#define STB_DS_IMPLEMENTATION 1 -#include "pc/utils/stb_ds.h" - -struct SyncObjectEntry { - u64 key; - struct SyncObject* value; -}; -struct SyncObjectEntry* sSoMap = NULL; +void* sSoMap = NULL; +void* sSoIter = NULL; struct SyncObjectForgetEntry { struct SyncObject* so; @@ -28,13 +23,17 @@ struct SyncObjectForgetEntry { struct SyncObjectForgetEntry* sForgetList = NULL; static u32 sNextSyncId = SYNC_ID_BLOCK_SIZE / 2; -static u32 sIterateIndex = 0; static bool sFreeingAll = false; //////////// // system // //////////// +void sync_objects_init_system(void) { + sSoMap = hmap_create(); + sSoIter = hmap_iter(sSoMap); +} + static bool sync_objects_forget_list_contains(struct SyncObject* so) { struct SyncObjectForgetEntry* entry = sForgetList; while (entry) { @@ -80,8 +79,7 @@ void sync_objects_clear(void) { sync_object_forget(so->id); } sFreeingAll = false; - hmfree(sSoMap); - hmdefault(sSoMap, NULL); + hmap_clear(sSoMap); } void sync_object_forget(u32 syncId) { @@ -111,7 +109,7 @@ void sync_object_forget(u32 syncId) { so->owned = false; if (!sFreeingAll) { - hmdel(sSoMap, syncId); + hmap_del(sSoMap, syncId); } // add it to a list to free later @@ -239,23 +237,15 @@ void sync_object_init_field_with_size(struct Object *o, void* field, u8 size) { struct SyncObject* sync_object_get(u32 syncId) { if (syncId == 0) { return NULL; } - return hmget(sSoMap, syncId); + return hmap_get(sSoMap, syncId); } struct SyncObject* sync_object_get_first(void) { - sIterateIndex = 0; - if (sSoMap && sIterateIndex < hmlen(sSoMap)) { - return sSoMap[sIterateIndex].value; - } - return NULL; + return hmap_begin(sSoIter); } struct SyncObject* sync_object_get_next(void) { - sIterateIndex++; - if (sSoMap && sIterateIndex < hmlen(sSoMap)) { - return sSoMap[sIterateIndex].value; - } - return NULL; + return hmap_next(sSoIter); } struct Object* sync_object_get_object(u32 syncId) { @@ -415,8 +405,8 @@ bool sync_object_set_id(struct Object* o) { so = calloc(1, sizeof(struct SyncObject)); so->id = syncId; so->extendedModelId = 0xFFFF; - hmput(sSoMap, syncId, so); - LOG_INFO("Allocated sync object @ %u, size %ld", syncId, hmlen(sSoMap)); + hmap_put(sSoMap, syncId, so); + LOG_INFO("Allocated sync object @ %u, size %ld", syncId, hmap_len(sSoMap)); } if (!so) { diff --git a/src/pc/network/sync_object.h b/src/pc/network/sync_object.h index 48e9651b..98f82826 100644 --- a/src/pc/network/sync_object.h +++ b/src/pc/network/sync_object.h @@ -41,6 +41,7 @@ struct SyncObject { //////////// // system // //////////// +void sync_objects_init_system(void); void sync_objects_update(void); void sync_objects_clear(void); void sync_object_forget(u32 syncId); diff --git a/src/pc/pc_main.c b/src/pc/pc_main.c index a087e0f6..bd0f5ef4 100644 --- a/src/pc/pc_main.c +++ b/src/pc/pc_main.c @@ -272,6 +272,7 @@ void main_func(void) { const char *userpath = gCLIOpts.SavePath[0] ? gCLIOpts.SavePath : sys_user_path(); fs_init(sys_ropaths, gamedir, userpath); + sync_objects_init_system(); mods_init(); configfile_load(configfile_name()); dynos_pack_init();