50 const size_t n = num_elems * elem_size;
51 const size_t alignment = 16;
53 if(n / elem_size != num_elems)
58 if(n < BOTAN_MLOCK_ALLOCATOR_MIN_ALLOCATION || n > BOTAN_MLOCK_ALLOCATOR_MAX_ALLOCATION)
61 lock_guard_type<mutex_type> lock(m_mutex);
63 auto best_fit = m_freelist.end();
65 for(
auto i = m_freelist.begin(); i != m_freelist.end(); ++i)
68 if(i->second == n && (i->first % alignment) == 0)
70 const size_t offset = i->first;
74 BOTAN_ASSERT((reinterpret_cast<size_t>(m_pool) + offset) % alignment == 0,
75 "Returning correctly aligned pointer");
77 return m_pool + offset;
80 if((i->second >= (n + padding_for_alignment(i->first, alignment)) &&
81 ((best_fit == m_freelist.end()) || (best_fit->second > i->second))))
87 if(best_fit != m_freelist.end())
89 const size_t offset = best_fit->first;
91 const size_t alignment_padding = padding_for_alignment(offset, alignment);
93 best_fit->first += n + alignment_padding;
94 best_fit->second -= n + alignment_padding;
106 if(best_fit->second == 0)
108 best_fit->first = offset;
109 best_fit->second = alignment_padding;
112 m_freelist.insert(best_fit, std::make_pair(offset, alignment_padding));
115 clear_mem(m_pool + offset + alignment_padding, n);
117 BOTAN_ASSERT((reinterpret_cast<size_t>(m_pool) + offset + alignment_padding) % alignment == 0,
118 "Returning correctly aligned pointer");
120 return m_pool + offset + alignment_padding;
void clear_mem(T *ptr, size_t n)
#define BOTAN_ASSERT(expr, assertion_made)