wip
This commit is contained in:
parent
1037256a30
commit
6f04aa9587
@ -13,19 +13,18 @@ namespace osrm::util
|
|||||||
{
|
{
|
||||||
|
|
||||||
#if 1
|
#if 1
|
||||||
template <typename T, size_t MinItemsInBlock = 1024> class PoolAllocator
|
template <typename T, size_t MinItemsInBlock = 1024>
|
||||||
|
class PoolAllocator;
|
||||||
|
|
||||||
|
template <typename T, size_t MinItemsInBlock = 1024>
|
||||||
|
class MemoryManager
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
using value_type = T;
|
static MemoryManager &instance()
|
||||||
|
|
||||||
PoolAllocator() noexcept = default;
|
|
||||||
|
|
||||||
template <typename U> PoolAllocator(const PoolAllocator<U> &) noexcept {}
|
|
||||||
|
|
||||||
template <typename U> struct rebind
|
|
||||||
{
|
{
|
||||||
using other = PoolAllocator<U, MinItemsInBlock>;
|
thread_local MemoryManager instance;
|
||||||
};
|
return instance;
|
||||||
|
}
|
||||||
|
|
||||||
T *allocate(std::size_t n)
|
T *allocate(std::size_t n)
|
||||||
{
|
{
|
||||||
@ -55,7 +54,7 @@ template <typename T, size_t MinItemsInBlock = 1024> class PoolAllocator
|
|||||||
free_lists_[free_list_index].push_back(p);
|
free_lists_[free_list_index].push_back(p);
|
||||||
}
|
}
|
||||||
|
|
||||||
~PoolAllocator()
|
~MemoryManager()
|
||||||
{
|
{
|
||||||
for (auto block : blocks_)
|
for (auto block : blocks_)
|
||||||
{
|
{
|
||||||
@ -63,44 +62,11 @@ template <typename T, size_t MinItemsInBlock = 1024> class PoolAllocator
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
PoolAllocator(const PoolAllocator &) = delete;
|
|
||||||
PoolAllocator &operator=(const PoolAllocator &) = delete;
|
|
||||||
|
|
||||||
PoolAllocator(PoolAllocator &&other) noexcept
|
|
||||||
: free_lists_(std::move(other.free_lists_)),
|
|
||||||
blocks_(std::move(other.blocks_)),
|
|
||||||
current_block_ptr_(other.current_block_ptr_),
|
|
||||||
current_block_left_items_(other.current_block_left_items_),
|
|
||||||
total_allocated_(other.total_allocated_)
|
|
||||||
{
|
|
||||||
other.current_block_ptr_ = nullptr;
|
|
||||||
other.current_block_left_items_ = 0;
|
|
||||||
other.total_allocated_ = 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
PoolAllocator &operator=(PoolAllocator &&other) noexcept
|
|
||||||
{
|
|
||||||
if (this != &other)
|
|
||||||
{
|
|
||||||
for (auto block : blocks_)
|
|
||||||
{
|
|
||||||
std::free(block);
|
|
||||||
}
|
|
||||||
|
|
||||||
free_lists_ = std::move(other.free_lists_);
|
|
||||||
blocks_ = std::move(other.blocks_);
|
|
||||||
current_block_ptr_ = other.current_block_ptr_;
|
|
||||||
current_block_left_items_ = other.current_block_left_items_;
|
|
||||||
total_allocated_ = other.total_allocated_;
|
|
||||||
|
|
||||||
other.current_block_ptr_ = nullptr;
|
|
||||||
other.current_block_left_items_ = 0;
|
|
||||||
other.total_allocated_ = 0;
|
|
||||||
}
|
|
||||||
return *this;
|
|
||||||
}
|
|
||||||
|
|
||||||
private:
|
private:
|
||||||
|
MemoryManager() = default;
|
||||||
|
MemoryManager(const MemoryManager &) = delete;
|
||||||
|
MemoryManager &operator=(const MemoryManager &) = delete;
|
||||||
|
|
||||||
size_t get_next_power_of_two_exponent(size_t n) const
|
size_t get_next_power_of_two_exponent(size_t n) const
|
||||||
{
|
{
|
||||||
BOOST_ASSERT(n > 0);
|
BOOST_ASSERT(n > 0);
|
||||||
@ -110,7 +76,7 @@ private:
|
|||||||
void allocate_block(size_t items_in_block)
|
void allocate_block(size_t items_in_block)
|
||||||
{
|
{
|
||||||
items_in_block = std::max(items_in_block, MinItemsInBlock);
|
items_in_block = std::max(items_in_block, MinItemsInBlock);
|
||||||
|
|
||||||
size_t block_size = items_in_block * sizeof(T);
|
size_t block_size = items_in_block * sizeof(T);
|
||||||
T *block = static_cast<T *>(std::malloc(block_size));
|
T *block = static_cast<T *>(std::malloc(block_size));
|
||||||
if (!block)
|
if (!block)
|
||||||
@ -131,6 +97,48 @@ private:
|
|||||||
size_t total_allocated_ = 0;
|
size_t total_allocated_ = 0;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
template <typename T, size_t MinItemsInBlock>
|
||||||
|
class PoolAllocator
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
using value_type = T;
|
||||||
|
|
||||||
|
PoolAllocator() noexcept = default;
|
||||||
|
|
||||||
|
template <typename U>
|
||||||
|
PoolAllocator(const PoolAllocator<U> &) noexcept {}
|
||||||
|
|
||||||
|
template <typename U>
|
||||||
|
struct rebind
|
||||||
|
{
|
||||||
|
using other = PoolAllocator<U, MinItemsInBlock>;
|
||||||
|
};
|
||||||
|
|
||||||
|
T *allocate(std::size_t n)
|
||||||
|
{
|
||||||
|
return MemoryManager<T, MinItemsInBlock>::instance().allocate(n);
|
||||||
|
}
|
||||||
|
|
||||||
|
void deallocate(T *p, std::size_t n) noexcept
|
||||||
|
{
|
||||||
|
MemoryManager<T, MinItemsInBlock>::instance().deallocate(p, n);
|
||||||
|
}
|
||||||
|
|
||||||
|
~PoolAllocator() = default;
|
||||||
|
|
||||||
|
PoolAllocator(const PoolAllocator &) = default;
|
||||||
|
PoolAllocator &operator=(const PoolAllocator &) = default;
|
||||||
|
PoolAllocator(PoolAllocator &&) noexcept = default;
|
||||||
|
PoolAllocator &operator=(PoolAllocator &&) noexcept = default;
|
||||||
|
|
||||||
|
private:
|
||||||
|
static size_t get_next_power_of_two_exponent(size_t n)
|
||||||
|
{
|
||||||
|
BOOST_ASSERT(n > 0);
|
||||||
|
return (sizeof(size_t) * 8) - std::countl_zero(n - 1);
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
template <typename T, typename U>
|
template <typename T, typename U>
|
||||||
bool operator==(const PoolAllocator<T> &, const PoolAllocator<U> &)
|
bool operator==(const PoolAllocator<T> &, const PoolAllocator<U> &)
|
||||||
{
|
{
|
||||||
|
@ -57,6 +57,21 @@ BOOST_AUTO_TEST_CASE(copy)
|
|||||||
pool2.deallocate(ptr, 1);
|
pool2.deallocate(ptr, 1);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
BOOST_AUTO_TEST_CASE(move)
|
||||||
|
{
|
||||||
|
PoolAllocator<int> pool;
|
||||||
|
auto ptr = pool.allocate(1);
|
||||||
|
*ptr = 42;
|
||||||
|
BOOST_CHECK_NE(ptr, nullptr);
|
||||||
|
pool.deallocate(ptr, 1);
|
||||||
|
|
||||||
|
PoolAllocator<int> pool2(std::move(pool));
|
||||||
|
ptr = pool2.allocate(1);
|
||||||
|
*ptr = 42;
|
||||||
|
BOOST_CHECK_NE(ptr, nullptr);
|
||||||
|
pool2.deallocate(ptr, 1);
|
||||||
|
}
|
||||||
|
|
||||||
BOOST_AUTO_TEST_CASE(unordered_map)
|
BOOST_AUTO_TEST_CASE(unordered_map)
|
||||||
{
|
{
|
||||||
std::unordered_map<int, int, std::hash<int>, std::equal_to<int>, PoolAllocator<std::pair<const int, int>>> map;
|
std::unordered_map<int, int, std::hash<int>, std::equal_to<int>, PoolAllocator<std::pair<const int, int>>> map;
|
||||||
|
Loading…
Reference in New Issue
Block a user