solidc
Robust collection of general-purpose cross-platform C libraries and data structures designed for rapid and safe development in C
Loading...
Searching...
No Matches
Typedefs | Functions
cache.h File Reference

Cache management utilities for performance optimization. More...

#include <stdbool.h>
#include <stddef.h>
#include <stdint.h>
Include dependency graph for cache.h:
This graph shows which files directly or indirectly include this file:

Go to the source code of this file.

Typedefs

typedef struct cache_s cache_t
 

Functions

cache_tcache_create (size_t capacity, uint32_t default_ttl)
 
void cache_destroy (cache_t *cache)
 
const void * cache_get (cache_t *cache, const char *key, size_t key_len, size_t *out_len)
 
void cache_release (const void *ptr)
 
bool cache_set (cache_t *cache, const char *key, size_t key_len, const void *value, size_t value_len, uint32_t ttl_override)
 
void cache_invalidate (cache_t *cache, const char *key)
 
void cache_clear (cache_t *cache)
 
size_t get_total_cache_size (cache_t *cache)
 
size_t get_total_capacity (cache_t *cache)
 
bool cache_save (cache_t *cache_ptr, const char *filename)
 
bool cache_load (cache_t *cache_ptr, const char *filename)
 

Detailed Description

Cache management utilities for performance optimization.

Definition in file cache.h.

Typedef Documentation

◆ cache_t

typedef struct cache_s cache_t

Opaque handle to the cache. Implementation details are hidden in cache.c to allow alignment optimizations without breaking ABI.

Definition at line 25 of file cache.h.

Function Documentation

◆ cache_clear()

void cache_clear ( cache_t cache_ptr)

Clears all entries from the cache index.

Removes all entries from the cache.

Definition at line 669 of file cache.c.

◆ cache_create()

cache_t * cache_create ( size_t  capacity,
uint32_t  default_ttl 
)

Creates a new cache.

Parameters
capacityTotal maximum number of entries (distributed across shards).
default_ttlDefault time-to-live in seconds.
Returns
Pointer to new cache, or NULL on failure.

Creates a new cache with the specified capacity and default TTL.

Definition at line 391 of file cache.c.

◆ cache_destroy()

void cache_destroy ( cache_t cache_ptr)

Destroys the cache and frees resources. Note: Zero-copy references held by users remain valid until cache_release() is called, even after the cache object is destroyed.

Destroys the cache and frees all associated memory.

Definition at line 434 of file cache.c.

◆ cache_get()

const void * cache_get ( cache_t cache_ptr,
const char *  key,
size_t  klen,
size_t *  out_len 
)

Zero-Copy Retrieval.

Parameters
cacheThe cache handle.
keyThe lookup key.
key_lenThe length of the key.
out_lenPointer to store the size of the retrieved value.
Returns
Pointer to the value data, or NULL if not found.
Note
YOU MUST CALL cache_release() on the returned pointer when done.

Retrieves a value from the cache by key.

On a hit the caller receives a pointer into the entry's data block. The entry's reference count is incremented before the lock is released, ensuring the memory remains valid even if another thread evicts the entry concurrently. The caller MUST call cache_release() when done with the pointer.

On expiry the function upgrades to a write lock to remove the stale entry. A double-check is performed after the upgrade because another thread may have refreshed or removed the entry between the read-unlock and write-lock. Compaction is intentionally NOT triggered here; that is deferred to the write path (cache_set, cache_invalidate) to avoid O(n) work on the read fast path.

Definition at line 467 of file cache.c.

◆ cache_invalidate()

void cache_invalidate ( cache_t cache_ptr,
const char *  key 
)

Invalidates (removes) an entry from the cache index.

Removes a key from the cache.

Definition at line 630 of file cache.c.

◆ cache_load()

bool cache_load ( cache_t cache_ptr,
const char *  filename 
)

Loads cache entries from a binary file.

Entries that are already expired in the file are skipped. Entries loaded will be subject to the current cache's eviction policy (if the file contains more items than the cache capacity).

Parameters
cache_ptrThe cache to load into.
filenameThe input file path.
Returns
true on success, false on I/O error or invalid format.

Loads entries from a file previously written by cache_save().

Entries whose expiry timestamp has already passed at load time are silently skipped. The TTL passed to cache_set is computed as the remaining lifetime (expiry - now), preserving the original expiration wall-clock time.

Key buffer strategy: a stack buffer (512 bytes) handles the common case. Oversized keys fall back to a heap buffer that is reused across iterations via realloc to avoid per-entry allocation.

Definition at line 828 of file cache.c.

References cache_set().

Here is the call graph for this function:

◆ cache_release()

void cache_release ( const void *  ptr)

Releases a reference to a zero-copy value.

Parameters
ptrThe pointer returned by cache_get().

Releases a reference to a cached value obtained from cache_get(). The caller must not access the pointer after calling this function.

Definition at line 661 of file cache.c.

◆ cache_save()

bool cache_save ( cache_t cache_ptr,
const char *  filename 
)

Serializes the current cache state to a binary file.

The operation locks shards one by one, allowing concurrent reads/writes to other shards while saving. The snapshot is not atomic across shards.

Parameters
cache_ptrThe cache to save.
filenameThe output file path.
Returns
true on success, false on I/O error.

Serialises all non-expired entries to a binary file.

File format: [magic:u32][version:u32][entry_count:u64] For each entry: [key_len:u32][value_len:u64][expires_at:i64][key_bytes:key_len][value_bytes:value_len]

entry_count is written as a placeholder (zero) in the header and patched to the actual count at the end via fseek, because expired entries are skipped during iteration and the true count is not known upfront.

Definition at line 752 of file cache.c.

◆ cache_set()

bool cache_set ( cache_t cache_ptr,
const char *  key,
size_t  klen,
const void *  value,
size_t  value_len,
uint32_t  ttl 
)

Stores a value in the cache.

Parameters
cacheThe cache handle.
keyThe key.
valueThe data to store.
value_lenThe length of the data.
ttl_overrideOptional TTL in seconds (0 uses default).
Returns
true on success, false on failure.

Inserts or updates a key-value pair in the cache.

The new entry is fully constructed outside the lock to minimize critical section duration. If the key already exists the old entry is replaced in-place (size unchanged). On a new insertion, eviction is triggered if the shard is at capacity.

Optimization vs. original: find_slot is called only ONCE per insert. The original code called find_slot a second time after clock_evict() returned, reasoning that the evicted slot might have invalidated idx. This was unnecessary:

  1. find_slot returns the best available insertion slot (empty or first tombstone).
  2. clock_evict() only converts a different live slot into a tombstone.
  3. compact_shard() is the only operation that reallocates shard->slots and invalidates all indices — but compaction is run before find_slot, not after. Therefore the original idx remains a valid insertion target after eviction.

Definition at line 550 of file cache.c.

Referenced by cache_load().

Here is the caller graph for this function:

◆ get_total_cache_size()

size_t get_total_cache_size ( cache_t cache_ptr)

Returns the total number of entries currently in the cache across all shards. Thread-safe: acquires read locks on all shards.

Parameters
cacheThe cache instance.
Returns
Total number of cached entries, or 0 if cache is NULL.

Returns the total number of live entries across all shards. Each shard is read-locked independently; the returned value is a consistent per-shard snapshot but not an atomic snapshot of the entire cache.

Definition at line 693 of file cache.c.

◆ get_total_capacity()

size_t get_total_capacity ( cache_t cache_ptr)

Returns the total capacity of the cache across all shards. Thread-safe: acquires read locks on all shards. Note: Capacity is set at creation and never changes, but we lock for consistency.

Parameters
cacheThe cache instance.
Returns
Total capacity, or 0 if cache is NULL.

Returns the total capacity across all shards. Capacity is set at creation time and does not change, so locking here is defensive rather than strictly necessary.

Definition at line 710 of file cache.c.