Flow
Documentation for the Flow C++ Library
Loading...
Searching...
No Matches
flow_stack_memory_resource.h
Go to the documentation of this file.
1#pragma once
4#include <cassert>
5#include <cstddef>
6#include <exception>
7
8namespace flow {
9
15 public:
16 explicit StackMemoryResource(void* buffer, std::size_t capacity) noexcept
17 : buffer_(buffer), capacity_(capacity) {
18 }
19
20 protected:
21 struct Header {
22 void* oldBuffer;
23 };
24
25 void* buffer_;
26 std::size_t capacity_;
27
28 virtual void* allocateImp(std::size_t bytes, std::size_t alignment) override {
29 void* oldBuffer = buffer_;
30
31 void* alignedHeader = flow::alignWithHeader<Header>(alignment, bytes, buffer_, capacity_);
32 if (!alignedHeader) {
33 throw std::bad_alloc();
34 }
35
36 new (alignedHeader) Header(oldBuffer);
37 void* allocatedBlock = reinterpret_cast<Header*>(alignedHeader) + 1;
38 buffer_ = reinterpret_cast<std::byte*>(allocatedBlock) + bytes;
39 capacity_ -= sizeof(Header) + bytes;
40 return allocatedBlock;
41 }
42
43 virtual void deallocateImp(void* address, std::size_t bytes, [[maybe_unused]] std::size_t alignment) override {
44 // TODO: assert address is the top most valid address
45 assert(address == nullptr || address <= buffer_);
46 if (!address) {
47 return;
48 }
49
50 Header* header = reinterpret_cast<Header*>(address) - 1;
51 std::size_t padding = pointerDistance(header->oldBuffer, header);
52 buffer_ = header->oldBuffer;
53 capacity_ += padding + sizeof(Header) + bytes;
54 header->~Header();
55 }
56 };
57}
A memory resource holder interface for the PolymorphicAllocator. Responsible for allocate and dealloc...
virtual void * allocateImp(std::size_t bytes, std::size_t alignment) override
virtual void deallocateImp(void *address, std::size_t bytes, std::size_t alignment) override
StackMemoryResource(void *buffer, std::size_t capacity) noexcept
std::size_t pointerDistance(const T *first, const U *last)
Calculate the distance in bytes from the first pointer to the last pointer.
Header * alignWithHeader(std::size_t alignment, std::size_t size, void *&buffer, std::size_t &capacity) noexcept
Align the header + buffer to their corresponding alignments. If the capacity is not big enough,...