19#include "pw_allocator/capability.h"
20#include "pw_allocator/deallocator.h"
21#include "pw_allocator/layout.h"
22#include "pw_allocator/unique_ptr.h"
23#include "pw_assert/assert.h"
24#include "pw_bytes/span.h"
25#include "pw_result/result.h"
27namespace pw::allocator {
38 constexpr const Layout& layout()
const {
return layout_; }
58 template <
typename T,
int&... kExplicitGuard,
typename... Args>
59 [[nodiscard]] std::enable_if_t<!std::is_array_v<T>, T*> New(Args&&... args);
62 int&... kExplicitGuard,
63 typename ElementType = std::remove_extent_t<T>>
64 [[nodiscard]] std::enable_if_t<pw::is_bounded_array_v<T>, ElementType*> New();
67 int&... kExplicitGuard,
68 typename ElementType = std::remove_extent_t<T>>
69 [[nodiscard]] std::enable_if_t<pw::is_unbounded_array_v<T>, ElementType*>
84 template <
typename T,
int&... kExplicitGuard,
typename... Args>
85 std::enable_if_t<!std::is_array_v<T>,
UniquePtr<T>> MakeUnique(
89 std::enable_if_t<pw::is_bounded_array_v<T>,
UniquePtr<T>> MakeUnique();
92 std::enable_if_t<pw::is_unbounded_array_v<T>,
UniquePtr<T>> MakeUnique();
104 template <
typename ElementType>
105 [[nodiscard]] ElementType* NewArray(
size_t count);
114template <
typename T,
int&... kExplicitGuard,
typename... Args>
115std::enable_if_t<!std::is_array_v<T>, T*> Pool::New(Args&&... args) {
116 PW_ASSERT(Layout::Of<T>() == layout_);
118 return ptr !=
nullptr ?
new (ptr) T(std::forward<Args>(args)...) :
nullptr;
121template <
typename T,
int&... kExplicitGuard,
typename ElementType>
122std::enable_if_t<pw::is_bounded_array_v<T>, ElementType*> Pool::New() {
123 return NewArray<ElementType>(std::extent_v<T>);
126template <
typename T,
int&... kExplicitGuard,
typename ElementType>
127std::enable_if_t<pw::is_unbounded_array_v<T>, ElementType*> Pool::New() {
128 return NewArray<ElementType>(layout_.size() /
sizeof(ElementType));
131template <
typename T,
int&... kExplicitGuard,
typename... Args>
134 return UniquePtr<T>(New<T>(std::forward<Args>(args)...), *
this);
138std::enable_if_t<pw::is_bounded_array_v<T>,
UniquePtr<T>> Pool::MakeUnique() {
139 using ElementType = std::remove_extent_t<T>;
140 return UniquePtr<T>(NewArray<ElementType>(std::extent_v<T>), *
this);
144std::enable_if_t<pw::is_unbounded_array_v<T>,
UniquePtr<T>> Pool::MakeUnique() {
145 using ElementType = std::remove_extent_t<T>;
146 size_t size = layout_.size() /
sizeof(ElementType);
147 return UniquePtr<T>(NewArray<ElementType>(size), size, *
this);
151template <
typename ElementType>
152ElementType* Pool::NewArray(
size_t count) {
153 Layout layout = Layout::Of<ElementType[]>(count);
154 PW_ASSERT(layout.size() == layout_.size());
155 PW_ASSERT(layout.alignment() <= layout_.alignment());
157 return ptr !=
nullptr ?
new (ptr) ElementType[count] :
nullptr;
Abstract interface for releasing memory.
Definition: deallocator.h:30
Definition: unique_ptr.h:44
Definition: capability.h:65
void * Allocate()
Definition: pool.h:45
virtual void * DoAllocate()=0