diff --git a/include/dice/template-library/pool_allocator.hpp b/include/dice/template-library/pool_allocator.hpp index 2953cb5..c71e7b1 100644 --- a/include/dice/template-library/pool_allocator.hpp +++ b/include/dice/template-library/pool_allocator.hpp @@ -3,8 +3,10 @@ #include +#include #include -#include +#include +#include namespace dice::template_library { @@ -55,14 +57,15 @@ namespace dice::template_library { pool *pool_; public: - explicit constexpr pool_allocator(pool &p) noexcept - : pool_{&p} { + explicit constexpr pool_allocator(pool &parent_pool) noexcept + : pool_{&parent_pool} { } constexpr pool_allocator(pool_allocator const &other) noexcept = default; constexpr pool_allocator(pool_allocator &&other) noexcept = default; constexpr pool_allocator &operator=(pool_allocator const &other) noexcept = default; constexpr pool_allocator &operator=(pool_allocator &&other) noexcept = default; + constexpr ~pool_allocator() noexcept = default; template constexpr pool_allocator(pool_allocator const &other) noexcept @@ -70,7 +73,7 @@ namespace dice::template_library { } constexpr pointer allocate(size_t n) { - return pool_->allocate(sizeof(T) * n); + return static_cast(pool_->allocate(sizeof(T) * n)); } constexpr void deallocate(pointer ptr, size_t n) { @@ -81,9 +84,9 @@ namespace dice::template_library { return pool_allocator{*pool_}; } - friend constexpr void swap(pool_allocator &a, pool_allocator &b) noexcept { + friend constexpr void swap(pool_allocator &lhs, pool_allocator &rhs) noexcept { using std::swap; - swap(a.pool_, b.pool_); + swap(lhs.pool_, rhs.pool_); } bool operator==(pool_allocator const &other) const noexcept = default; @@ -108,7 +111,7 @@ namespace dice::template_library { template void *allocate_impl(size_t n_bytes) { - if (n_bytes < bucket_size) { + if (n_bytes <= bucket_size) { // fits into bucket void *ptr = pools_[ix].malloc(); @@ -129,16 +132,17 @@ namespace dice::template_library { template void deallocate_impl(void *data, size_t n_bytes) { - if (n_bytes < bucket_size) { + if (n_bytes <= bucket_size) { // fits into bucket pools_[ix].free(data); + return; } if constexpr (sizeof...(rest) > 0) { - return deallocate_impl(data, n_bytes); + deallocate_impl(data, n_bytes); } else { // does not fit into any bucket, must have been allocated via new[] - return delete[] static_cast(data); + delete[] static_cast(data); } } diff --git a/tests/tests_pool_allocator.cpp b/tests/tests_pool_allocator.cpp index d44e058..cf2b64f 100644 --- a/tests/tests_pool_allocator.cpp +++ b/tests/tests_pool_allocator.cpp @@ -3,11 +3,25 @@ #include +#include +#include +#include + TEST_SUITE("pool allocator") { TEST_CASE("sanity check") { dice::template_library::pool<8, 16> pool; + auto alloc1 = pool.get_allocator(); // first pool + auto alloc2 = pool.get_allocator>(); // second pool + auto alloc3 = pool.get_allocator>(); // fallback to new + for (size_t ix = 0; ix < 1'000'000; ++ix) { + auto *ptr1 = alloc1.allocate(1); + auto *ptr2 = alloc2.allocate(1); + auto *ptr3 = alloc3.allocate(1); - + alloc2.deallocate(ptr2, 1); + alloc3.deallocate(ptr3, 1); + alloc1.deallocate(ptr1, 1); + } } }