Allow heap_manager to use non-contiguous blocks.

* Heap manager can now manage non-contiguous blocks of memory (currently
  all sized at the max block size only)
* Fix a bug where heap manager would try to buddy-merge max-sized blocks
This commit is contained in:
Justin C. Miller
2019-02-18 23:27:24 -08:00
parent 61df9cf32c
commit a9ac30b991
4 changed files with 97 additions and 18 deletions

View File

@@ -104,7 +104,7 @@ heap_manager::free(void *p)
header -= 1; // p points after the header
header->set_used(false);
while (true) {
while (header->size() != max_size) {
mem_header *buddy = header->buddy();
if (buddy->used() || buddy->size() != header->size()) break;
buddy->remove();
@@ -124,9 +124,8 @@ heap_manager::grow_memory()
{
size_t length = (1 << max_size);
void *next = kutil::offset_pointer(m_start, m_length);
kassert(m_grow, "Tried to grow heap without a growth callback");
m_grow(next, length);
void *next = m_grow(kutil::offset_pointer(m_start, m_length), length);
mem_header *block = new (next) mem_header(nullptr, get_free(max_size), max_size);
get_free(max_size) = block;

View File

@@ -11,7 +11,10 @@ namespace kutil {
class heap_manager
{
public:
using grow_callback = void (*)(void *start, size_t length);
/// Callback signature for growth function. The next pointer is just a
/// hint; memory returned does not need to be contiguous, but needs to be
/// alined to the length requested.
using grow_callback = void * (*)(void *next, size_t length);
/// Default constructor. Creates an invalid manager.
heap_manager();