Skip to content

Commit

Permalink
Remove LDKChunck from arena.h
Browse files Browse the repository at this point in the history
  • Loading branch information
marciovmf committed Oct 24, 2024
1 parent 065e307 commit 5d64a41
Show file tree
Hide file tree
Showing 3 changed files with 109 additions and 20 deletions.
76 changes: 65 additions & 11 deletions include/ldk/arena.h
Original file line number Diff line number Diff line change
Expand Up @@ -18,12 +18,7 @@
extern "C" {
#endif

typedef struct
{
uint8* data;
size_t used;
size_t capacity;
} LDKChunk;
typedef struct LDKChunk_t LDKChunk;

typedef struct
{
Expand All @@ -32,13 +27,72 @@ extern "C" {
size_t chunkCapacity;
} LDKArena;


/**
* ldkArenaAllocate
*
* A macro that simplifies memory allocation from the arena for a specific type.
* It automatically calculates the size of the type and calls `ldkArenaAllocateSize`
* to allocate the appropriate amount of memory from the arena.
*
* @param arena Pointer to the arena from which memory is to be allocated.
* @param type The data type for which memory is to be allocated.
* @return Returns a pointer to the allocated memory for the given type, or NULL if allocation fails.
*/
#define ldkArenaAllocate(arena, type) ldkArenaAllocateSize(arena, sizeof(type))

LDK_API bool ldkArenaCreate(LDKArena* out, size_t chunkSize);
LDK_API void ldkArenaDestroy(LDKArena* arena);
LDK_API uint8* ldkArenaAllocateSize(LDKArena* arena, size_t size); // gets memory from chunk
LDK_API void ldkArenaReset(LDKArena* arena);
/**
* ldkArenaCreate
*
* Initializes an arena with an initial chunk size. The arena can allocate memory
* as needed from chunks, and more chunks are added dynamically if required.
*
* @param out Pointer to the arena to be initialized.
* @param chunkSize The size of the initial chunk to allocate for the arena.
* @return Returns true if the arena is successfully created, otherwise false.
*/
LDK_API bool ldkArenaCreate(LDKArena* out, size_t chunkSize);

/**
* ldkArenaDestroy
*
* Frees all memory used by the arena and deallocates all chunks.
* After calling this function, the arena is no longer valid and
* should not be used unless re-initialized.
*
* @param arena Pointer to the arena to be destroyed.
*/
LDK_API void ldkArenaDestroy(LDKArena* arena);

/**
* ldkArenaAllocateSize
*
* Allocates memory of the specified size from the current chunk in the arena.
* If there isn't enough memory in the current chunk, a new chunk is allocated.
*
* @param arena Pointer to the arena from which memory is to be allocated.
* @param size The amount of memory to allocate in bytes.
* @return Returns a pointer to the allocated memory, or NULL if allocation fails.
*/
LDK_API uint8* ldkArenaAllocateSize(LDKArena* arena, size_t size);
/**
* ldkArenaReset
*
* Resets the arena by releasing all memory from all chunks, but keeps the
* allocated chunks ready for reuse. This allows future allocations without
* needing to destroy and recreate the arena, reducing allocation overhead.
*
* @param arena Pointer to the arena to be reset.
*/
LDK_API void ldkArenaReset(LDKArena* arena);


//
// Query per chunk information.
// These are unlikely to be used unless for debug/test code
//
LDK_API size_t ldkArenaGetChunkCpacity(LDKArena* arena, uint32 chunkIndex);
LDK_API size_t ldkArenaGetChunkUsed(LDKArena* arena, uint32 chunkIndex);
LDK_API uint8* ldkArenaGetChunkDataPtr(LDKArena* arena, uint32 chunkIndex);


#ifdef __cplusplus
Expand Down
35 changes: 35 additions & 0 deletions src/arena.c
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,19 @@
#define ARENA_REALLOC(mem, size) ldkOsMemoryResize(mem, size)
#endif // ARENA_REALLOC

/**
* LDKChunk
*
* Represents a block of memory that is used by the arena. Each chunk has a fixed
* capacity and tracks how much of it has been used.
*/
struct LDKChunk_t
{
uint8* data;
size_t used;
size_t capacity;
};

//
// Internal functions
//
Expand Down Expand Up @@ -106,6 +119,28 @@ uint8* ldkArenaAllocateSize(LDKArena* arena, size_t size)
return s_arenaAllocateFromLDKChunk(chunk, size);
}


size_t ldkArenaGetChunkCpacity(LDKArena* arena, uint32 chunkIndex)
{
if(arena->numChunks <= chunkIndex)
return -1;
return arena->chunks[chunkIndex].capacity;
}

size_t ldkArenaGetChunkUsed(LDKArena* arena, uint32 chunkIndex)
{
if(arena->numChunks <= chunkIndex)
return -1;
return arena->chunks[chunkIndex].used;
}

uint8* ldkArenaGetChunkDataPtr(LDKArena* arena, uint32 chunkIndex)
{
if(arena->numChunks <= chunkIndex)
return NULL;
return arena->chunks[chunkIndex].data;
}

void ldkArenaReset(LDKArena* arena)
{
for (uint32 i = 0; i < arena->numChunks; i++)
Expand Down
18 changes: 9 additions & 9 deletions src/tests/test_arena.c
Original file line number Diff line number Diff line change
Expand Up @@ -12,9 +12,9 @@ int test_ldkArenaCreate()
ASSERT_TRUE(result == true);
ASSERT_TRUE(arena.numChunks == 1);
ASSERT_TRUE(arena.chunkCapacity == chunkSize);
ASSERT_TRUE(arena.chunks[0].capacity == chunkSize);
ASSERT_TRUE(arena.chunks[0].used == 0);
ASSERT_TRUE(arena.chunks[0].data != NULL);
ASSERT_TRUE(ldkArenaGetChunkCpacity(&arena, 0) == chunkSize);
ASSERT_TRUE(ldkArenaGetChunkUsed(&arena, 0) == 0);
ASSERT_TRUE(ldkArenaGetChunkDataPtr(&arena, 0) != NULL);
ldkArenaDestroy(&arena);
return 0;
}
Expand All @@ -37,18 +37,18 @@ int test_ldkArenaAllocateSize()

uint8* mem1 = ldkArenaAllocateSize(&arena, 128);
ASSERT_TRUE(mem1 != NULL);
ASSERT_TRUE(arena.chunks[0].used == 128);
ASSERT_TRUE(ldkArenaGetChunkUsed(&arena, 0) == 128);

uint8* mem2 = ldkArenaAllocateSize(&arena, 512);
ASSERT_TRUE(mem2 != NULL);
ASSERT_TRUE(arena.chunks[0].used == 640);
ASSERT_TRUE(ldkArenaGetChunkUsed(&arena, 0) == 640);

uint8* mem3 = ldkArenaAllocateSize(&arena, 512);
ASSERT_TRUE(mem3 != NULL);

ASSERT_TRUE(arena.numChunks == 2);
ASSERT_TRUE(arena.chunks[0].used == 640);
ASSERT_TRUE(arena.chunks[1].used == 512);
ASSERT_TRUE(ldkArenaGetChunkUsed(&arena, 0) == 640);
ASSERT_TRUE(ldkArenaGetChunkUsed(&arena, 1) == 512);

ldkArenaDestroy(&arena);
return 0;
Expand All @@ -64,12 +64,12 @@ int test_ldkArenaReset()

ldkArenaReset(&arena);
ASSERT_TRUE(arena.numChunks == 1);
ASSERT_TRUE(arena.chunks[0].used == 0);
ASSERT_TRUE(ldkArenaGetChunkUsed(&arena, 0) == 0);

ldkArenaAllocateSize(&arena, 512);
ldkArenaAllocateSize(&arena, 512);
ASSERT_TRUE(arena.numChunks == 1);
ASSERT_TRUE(arena.chunks[0].used == 1024);
ASSERT_TRUE(ldkArenaGetChunkUsed(&arena, 0) == 1024);

ldkArenaDestroy(&arena);
return 0;
Expand Down

0 comments on commit 5d64a41

Please sign in to comment.