Skip to content

Commit 3a9b061

Browse files
authored
Fix: add cache free hook and default param free (#253)
* Add cache free hook and default param free * Enhance error handling for parsing * Unify description and close handle
1 parent 5f47024 commit 3a9b061

File tree

4 files changed

+43
-1
lines changed

4 files changed

+43
-1
lines changed

example/plugin_v2/README.md

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -43,6 +43,7 @@ The plugin implements these required hook functions:
4343
- `cache_miss_hook()` - Handle cache misses (insert new object)
4444
- `cache_eviction_hook()` - Evict least recently used object and return its ID
4545
- `cache_remove_hook()` - Remove specific object from cache
46+
- `cache_free_hook()` - Clean up and free the LRU cache data structure
4647

4748
## Usage
4849

example/plugin_v2/plugin_lru.cpp

Lines changed: 8 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -134,4 +134,11 @@ void cache_remove_hook(void *data, const obj_id_t obj_id) {
134134
lru_cache->cache_remove(obj_id);
135135
}
136136

137-
} // extern "C"
137+
// implement the cache free hook
138+
void cache_free_hook(void *data) {
139+
// free the LRU cache (destructor handles all cleanup)
140+
StandaloneLRU *lru_cache = (StandaloneLRU *)data;
141+
delete lru_cache;
142+
}
143+
144+
} // extern "C"

libCacheSim/cache/eviction/plugin_cache.c

Lines changed: 23 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -13,6 +13,7 @@
1313
* - cache_miss_hook: Handle cache miss events
1414
* - cache_eviction_hook: Determine which object to evict
1515
* - cache_remove_hook: Clean up when objects are removed
16+
* - cache_free_hook: Free plugin resources
1617
*
1718
* The plugin cache delegates core cache operations to these hooks, enabling
1819
* flexible and extensible cache policies.
@@ -46,12 +47,14 @@ extern "C" {
4647
*/
4748
typedef struct pluginCache_params {
4849
char *plugin_path; ///< Path to the plugin shared library
50+
void *plugin_handle; ///< Handle to the loaded plugin library
4951
void *data; ///< Plugin's internal data structure
5052
cache_init_hook_t cache_init_hook; ///< Plugin initialization function
5153
cache_hit_hook_t cache_hit_hook; ///< Cache hit handler function
5254
cache_miss_hook_t cache_miss_hook; ///< Cache miss handler function
5355
cache_eviction_hook_t cache_eviction_hook; ///< Eviction decision function
5456
cache_remove_hook_t cache_remove_hook; ///< Object removal handler function
57+
cache_free_hook_t cache_free_hook; ///< Cache cleanup function
5558
char *cache_name;
5659
} pluginCache_params_t;
5760

@@ -137,6 +140,7 @@ cache_t *pluginCache_init(const common_cache_params_t ccache_params,
137140
ERROR("Failed to load plugin %s: %s\n", params->plugin_path, dlerror());
138141
exit(1);
139142
}
143+
params->plugin_handle = handle;
140144

141145
// Load hook functions from the plugin using unions to avoid pedantic warnings
142146
union {
@@ -159,6 +163,10 @@ cache_t *pluginCache_init(const common_cache_params_t ccache_params,
159163
void *obj;
160164
cache_remove_hook_t func;
161165
} cache_remove_u;
166+
union {
167+
void *obj;
168+
cache_free_hook_t func;
169+
} cache_free_u;
162170

163171
cache_init_u.obj = dlsym(handle, "cache_init_hook");
164172
params->cache_init_hook = cache_init_u.func;
@@ -175,6 +183,9 @@ cache_t *pluginCache_init(const common_cache_params_t ccache_params,
175183
cache_remove_u.obj = dlsym(handle, "cache_remove_hook");
176184
params->cache_remove_hook = cache_remove_u.func;
177185

186+
cache_free_u.obj = dlsym(handle, "cache_free_hook");
187+
params->cache_free_hook = cache_free_u.func;
188+
178189
// Initialize the plugin with cache parameters
179190
params->data = params->cache_init_hook(ccache_params);
180191

@@ -205,6 +216,10 @@ cache_t *pluginCache_init(const common_cache_params_t ccache_params,
205216
*/
206217
static void pluginCache_free(cache_t *cache) {
207218
pluginCache_params_t *params = (pluginCache_params_t *)cache->eviction_params;
219+
220+
if (params->cache_free_hook != NULL) params->cache_free_hook(params->data);
221+
if (params->plugin_handle != NULL)
222+
dlclose(params->plugin_handle); // Close the plugin shared library handle
208223
if (params->plugin_path != NULL) free(params->plugin_path);
209224
if (params->cache_name != NULL) free(params->cache_name);
210225
free(cache->eviction_params);
@@ -398,8 +413,16 @@ static void pluginCache_parse_params(cache_t *cache,
398413

399414
// Process recognized parameters
400415
if (strcasecmp(key, "plugin") == 0 || strcasecmp(key, "plugin_path") == 0) {
416+
// Validate plugin path is not empty
417+
if (strlen(value) == 0) {
418+
ERROR("Parameter 'plugin_path' cannot be empty in cache '%s'\n",
419+
cache->cache_name);
420+
exit(1);
421+
}
422+
if (params->plugin_path != NULL) free(params->plugin_path);
401423
params->plugin_path = strdup(value);
402424
} else if (strcasecmp(key, "cache_name") == 0) {
425+
if (params->cache_name != NULL) free(params->cache_name);
403426
params->cache_name = strdup(value);
404427
} else if (strcasecmp(key, "print") == 0) {
405428
printf("current parameters: plugin_path=%s\n", params->plugin_path);

libCacheSim/include/libCacheSim/plugin.h

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -109,6 +109,7 @@ cache_t *create_cache_external(const char *const cache_alg_name,
109109
* - cache_miss_hook: Handle cache miss events
110110
* - cache_eviction_hook: Determine which object to evict
111111
* - cache_remove_hook: Clean up when objects are removed
112+
* - cache_free_hook: Free plugin resources
112113
*
113114
* @see example/plugin_v2/plugin_lru.c for a complete implementation example
114115
* @{
@@ -186,6 +187,16 @@ typedef obj_id_t (*cache_eviction_hook_t)(void *data, const request_t *req);
186187
*/
187188
typedef void (*cache_remove_hook_t)(void *data, const obj_id_t obj_id);
188189

190+
/**
191+
* @brief Cache free hook function type
192+
*
193+
* Cleanup function called when the cache is being destroyed.
194+
* The plugin should free any resources allocated in cache_init_hook.
195+
*
196+
* @param data Pointer to plugin's internal data (from cache_init_hook)
197+
*/
198+
typedef void (*cache_free_hook_t)(void *data);
199+
189200
/** @} */ // end of v2_plugin_api group
190201

191202
#ifdef __cplusplus

0 commit comments

Comments
 (0)