DeterministicESPAsyncWebServer v6.27.1
Zero-allocation, bounded-execution async HTTP server for ESP32
Loading...
Searching...
No Matches
arena.h File Reference

Unified double-ended server arena (Phase 1: core allocator, one region). More...

#include <stddef.h>
#include <stdint.h>

Go to the source code of this file.

Classes

struct  DetArena
 Double-ended arena over one region [base, base+size). More...
 
struct  DetArenaSet
 A set of DetArena regions searched in insertion (preference) order. More...
 
struct  DetArenaMark
 A scratch savepoint across every region of a DetArenaSet. More...
 

Macros

#define DET_ARENA_ALIGN   8u
 Baseline alignment (bytes) applied to every allocation and to headers.
 
#define DET_ARENA_MAX_ALIGN   16u
 Strongest alignment a scratch borrow may request; the region base is aligned to it.
 
#define DET_ARENA_MAX_REGIONS   2u
 Max regions in a DetArenaSet (DRAM base + PSRAM extension).
 

Functions

void det_arena_init (DetArena *a, void *base, size_t size)
 Initialize a over the region [base, base+size).
 
void * det_arena_persist_alloc (DetArena *a, size_t n)
 Allocate n zero-initialized bytes of long-lived storage.
 
void det_arena_persist_free (DetArena *a, void *p)
 Free a pointer previously returned by det_arena_persist_alloc().
 
void * det_arena_scratch_alloc_aligned (DetArena *a, size_t n, size_t align)
 Bump-allocate n bytes of transient storage, aligned to align.
 
void * det_arena_scratch_alloc (DetArena *a, size_t n)
 Bump-allocate n transient bytes at the baseline alignment (DET_ARENA_ALIGN).
 
size_t det_arena_scratch_mark (const DetArena *a)
 Capture the current scratch position (a savepoint for det_arena_scratch_release()).
 
void det_arena_scratch_release (DetArena *a, size_t mark)
 Free every scratch allocation made since mark (a value from det_arena_scratch_mark()).
 
void det_arena_scratch_reset (DetArena *a)
 Free ALL scratch allocations in O(1).
 
size_t det_arena_free_bytes (const DetArena *a)
 Free bytes in the middle (max a single new allocation could take, minus a header).
 
size_t det_arena_persist_used (const DetArena *a)
 Persistent payload bytes currently allocated.
 
size_t det_arena_scratch_used (const DetArena *a)
 Scratch bytes currently allocated.
 
void det_arena_set_init (DetArenaSet *s)
 Initialize an empty set (no regions yet).
 
bool det_arena_set_add (DetArenaSet *s, void *base, size_t size)
 Add a region [base, base+size); regions are searched in the order added.
 
void * det_arena_set_persist_alloc (DetArenaSet *s, size_t n)
 Persistent alloc from the first region that fits (see det_arena_persist_alloc()).
 
void det_arena_set_persist_free (DetArenaSet *s, void *p)
 Free a persistent pointer, routed to its owning region by address.
 
void * det_arena_set_scratch_alloc_aligned (DetArenaSet *s, size_t n, size_t align)
 Aligned scratch alloc from the first region that fits (see det_arena_scratch_alloc_aligned()).
 
void * det_arena_set_scratch_alloc (DetArenaSet *s, size_t n)
 Scratch alloc from the first region that fits (see det_arena_scratch_alloc()).
 
DetArenaMark det_arena_set_scratch_mark (const DetArenaSet *s)
 Capture the scratch position of every region.
 
void det_arena_set_scratch_release (DetArenaSet *s, const DetArenaMark *m)
 Restore every region's scratch position to m (frees scratch made since).
 
void det_arena_set_scratch_reset (DetArenaSet *s)
 Reset scratch in every region.
 
size_t det_arena_set_free_bytes (const DetArenaSet *s)
 Total free middle bytes summed over all regions.
 
size_t det_arena_set_persist_used (const DetArenaSet *s)
 Persistent payload bytes allocated, summed over all regions.
 
size_t det_arena_set_scratch_used (const DetArenaSet *s)
 Scratch bytes allocated, summed over all regions.
 

Detailed Description

Unified double-ended server arena (Phase 1: core allocator, one region).

One contiguous region is shared by two allocators that grow toward each other, with the free space floating in the middle:

[ persistent –grows up--> | free | <–grows down– scratch ] low addr (floating boundary) high addr

  • Persistent (bottom): a first-fit free-list. Long-lived objects that are freed individually, in arbitrary order (e.g. per-connection state). Grows up into the middle only as far as the scratch end allows; a freed top block shrinks it back.
  • Scratch (top): a bump allocator reclaimed in bulk. Transient per-dispatch buffers. scratch_reset() empties it in O(1); mark/release give nested savepoints.

Whichever side needs more room grows into the shared middle - that is the win over two fixed pools. Both ends fail closed (return NULL) rather than crossing the boundary.

All state lives in DetArena (no globals), so it is unit-testable and can back several arenas (a DRAM base and a PSRAM extension, in a later phase). No heap; no stdlib.

Author
Douglas Quigg (dstroy0)
Date
2026

Definition in file arena.h.

Macro Definition Documentation

◆ DET_ARENA_ALIGN

#define DET_ARENA_ALIGN   8u

Baseline alignment (bytes) applied to every allocation and to headers.

Definition at line 37 of file arena.h.

◆ DET_ARENA_MAX_ALIGN

#define DET_ARENA_MAX_ALIGN   16u

Strongest alignment a scratch borrow may request; the region base is aligned to it.

Definition at line 40 of file arena.h.

◆ DET_ARENA_MAX_REGIONS

#define DET_ARENA_MAX_REGIONS   2u

Max regions in a DetArenaSet (DRAM base + PSRAM extension).

Definition at line 135 of file arena.h.

Function Documentation

◆ det_arena_init()

void det_arena_init ( DetArena a,
void *  base,
size_t  size 
)

Initialize a over the region [base, base+size).

base should be DET_ARENA_ALIGN-aligned; size must be at least a few blocks.

Definition at line 29 of file arena.cpp.

References DetArena::base, DET_ARENA_ALIGN, DET_ARENA_MAX_ALIGN, DetArena::persist_end, DetArena::persist_hw, DetArena::persist_used, DetArena::scratch_hw, DetArena::scratch_top, and DetArena::size.

Referenced by det_arena_set_add().

◆ det_arena_persist_alloc()

void * det_arena_persist_alloc ( DetArena a,
size_t  n 
)

Allocate n zero-initialized bytes of long-lived storage.

First-fits an existing free block; otherwise carves a new block from the free middle (growing the persistent end up) if it will not cross the scratch end.

Returns
aligned, zeroed pointer, or NULL if the arena cannot satisfy it.

Definition at line 49 of file arena.cpp.

References DetArena::base, DET_ARENA_ALIGN, DetArena::persist_end, DetArena::persist_hw, and DetArena::persist_used.

Referenced by det_arena_set_persist_alloc().

◆ det_arena_persist_free()

void det_arena_persist_free ( DetArena a,
void *  p 
)

Free a pointer previously returned by det_arena_persist_alloc().

Coalesces with adjacent free blocks; if the freed block sits at the top of the persistent region it returns that space to the free middle (shrinks the boundary). Passing NULL is a no-op.

Definition at line 96 of file arena.cpp.

References DetArena::base, DetArena::persist_end, and DetArena::persist_used.

Referenced by det_arena_set_persist_free().

◆ det_arena_scratch_alloc_aligned()

void * det_arena_scratch_alloc_aligned ( DetArena a,
size_t  n,
size_t  align 
)

Bump-allocate n bytes of transient storage, aligned to align.

Parameters
alignpower-of-two alignment for the returned pointer; clamped to [DET_ARENA_ALIGN, DET_ARENA_MAX_ALIGN].
Returns
aligned pointer (NOT zeroed), or NULL if it would cross the persistent end.

Definition at line 143 of file arena.cpp.

References DetArena::base, DET_ARENA_ALIGN, DET_ARENA_MAX_ALIGN, DetArena::scratch_hw, DetArena::scratch_top, and DetArena::size.

Referenced by det_arena_scratch_alloc(), and det_arena_set_scratch_alloc_aligned().

◆ det_arena_scratch_alloc()

void * det_arena_scratch_alloc ( DetArena a,
size_t  n 
)

Bump-allocate n transient bytes at the baseline alignment (DET_ARENA_ALIGN).

Definition at line 163 of file arena.cpp.

References DET_ARENA_ALIGN, and det_arena_scratch_alloc_aligned().

◆ det_arena_scratch_mark()

size_t det_arena_scratch_mark ( const DetArena a)

Capture the current scratch position (a savepoint for det_arena_scratch_release()).

Definition at line 168 of file arena.cpp.

References DetArena::scratch_top.

◆ det_arena_scratch_release()

void det_arena_scratch_release ( DetArena a,
size_t  mark 
)

Free every scratch allocation made since mark (a value from det_arena_scratch_mark()).

Definition at line 173 of file arena.cpp.

References DetArena::scratch_top.

Referenced by det_arena_set_scratch_release().

◆ det_arena_scratch_reset()

void det_arena_scratch_reset ( DetArena a)

Free ALL scratch allocations in O(1).

Definition at line 180 of file arena.cpp.

References DetArena::scratch_top, and DetArena::size.

Referenced by det_arena_set_scratch_reset().

◆ det_arena_free_bytes()

size_t det_arena_free_bytes ( const DetArena a)

Free bytes in the middle (max a single new allocation could take, minus a header).

Definition at line 189 of file arena.cpp.

References DetArena::persist_end, and DetArena::scratch_top.

Referenced by det_arena_set_free_bytes().

◆ det_arena_persist_used()

size_t det_arena_persist_used ( const DetArena a)

Persistent payload bytes currently allocated.

Definition at line 195 of file arena.cpp.

References DetArena::persist_used.

Referenced by det_arena_set_persist_used().

◆ det_arena_scratch_used()

size_t det_arena_scratch_used ( const DetArena a)

Scratch bytes currently allocated.

Definition at line 200 of file arena.cpp.

References DetArena::scratch_top, and DetArena::size.

Referenced by det_arena_set_scratch_used().

◆ det_arena_set_init()

void det_arena_set_init ( DetArenaSet s)

Initialize an empty set (no regions yet).

Definition at line 209 of file arena.cpp.

References DetArenaSet::count.

◆ det_arena_set_add()

bool det_arena_set_add ( DetArenaSet s,
void *  base,
size_t  size 
)

Add a region [base, base+size); regions are searched in the order added.

Returns
true if added, false if the set is full or the region is too small.

Definition at line 214 of file arena.cpp.

References DetArenaSet::count, DET_ARENA_ALIGN, det_arena_init(), DET_ARENA_MAX_REGIONS, DetArenaSet::region, and DetArena::size.

◆ det_arena_set_persist_alloc()

void * det_arena_set_persist_alloc ( DetArenaSet s,
size_t  n 
)

Persistent alloc from the first region that fits (see det_arena_persist_alloc()).

Definition at line 226 of file arena.cpp.

References DetArenaSet::count, det_arena_persist_alloc(), and DetArenaSet::region.

◆ det_arena_set_persist_free()

void det_arena_set_persist_free ( DetArenaSet s,
void *  p 
)

Free a persistent pointer, routed to its owning region by address.

Definition at line 237 of file arena.cpp.

References DetArena::base, DetArenaSet::count, det_arena_persist_free(), DetArenaSet::region, and DetArena::size.

◆ det_arena_set_scratch_alloc_aligned()

void * det_arena_set_scratch_alloc_aligned ( DetArenaSet s,
size_t  n,
size_t  align 
)

Aligned scratch alloc from the first region that fits (see det_arena_scratch_alloc_aligned()).

Definition at line 253 of file arena.cpp.

References DetArenaSet::count, det_arena_scratch_alloc_aligned(), and DetArenaSet::region.

Referenced by det_arena_set_scratch_alloc().

◆ det_arena_set_scratch_alloc()

void * det_arena_set_scratch_alloc ( DetArenaSet s,
size_t  n 
)

Scratch alloc from the first region that fits (see det_arena_scratch_alloc()).

Definition at line 264 of file arena.cpp.

References DET_ARENA_ALIGN, and det_arena_set_scratch_alloc_aligned().

◆ det_arena_set_scratch_mark()

DetArenaMark det_arena_set_scratch_mark ( const DetArenaSet s)

Capture the scratch position of every region.

Definition at line 269 of file arena.cpp.

References DetArenaSet::count, DetArenaMark::count, DetArenaSet::region, DetArena::scratch_top, and DetArenaMark::top.

◆ det_arena_set_scratch_release()

void det_arena_set_scratch_release ( DetArenaSet s,
const DetArenaMark m 
)

Restore every region's scratch position to m (frees scratch made since).

Definition at line 278 of file arena.cpp.

References DetArenaSet::count, DetArenaMark::count, det_arena_scratch_release(), DetArenaSet::region, and DetArenaMark::top.

◆ det_arena_set_scratch_reset()

void det_arena_set_scratch_reset ( DetArenaSet s)

Reset scratch in every region.

Definition at line 285 of file arena.cpp.

References DetArenaSet::count, det_arena_scratch_reset(), and DetArenaSet::region.

◆ det_arena_set_free_bytes()

size_t det_arena_set_free_bytes ( const DetArenaSet s)

Total free middle bytes summed over all regions.

Definition at line 291 of file arena.cpp.

References DetArenaSet::count, det_arena_free_bytes(), and DetArenaSet::region.

◆ det_arena_set_persist_used()

size_t det_arena_set_persist_used ( const DetArenaSet s)

Persistent payload bytes allocated, summed over all regions.

Definition at line 299 of file arena.cpp.

References DetArenaSet::count, det_arena_persist_used(), and DetArenaSet::region.

◆ det_arena_set_scratch_used()

size_t det_arena_set_scratch_used ( const DetArenaSet s)

Scratch bytes allocated, summed over all regions.

Definition at line 307 of file arena.cpp.

References DetArenaSet::count, det_arena_scratch_used(), and DetArenaSet::region.