38 #ifndef LIBPMEMOBJ_SEGMENT_VECTOR_POLICIES_HPP
39 #define LIBPMEMOBJ_SEGMENT_VECTOR_POLICIES_HPP
50 namespace segment_vector_internal
53 using array_64 = array<T, 64>;
55 template <
typename Container>
57 decltype(std::declval<Container>().resize(std::declval<size_t>()));
59 template <
typename Container>
60 using container_has_resize = detail::supports<Container, resize_method>;
62 template <typename Container, bool = container_has_resize<Container>::value>
63 struct segment_vector_resize {
64 using segment_vector_type = Container;
67 resize(segment_vector_type &c,
size_t n)
73 template <
typename Container>
74 struct segment_vector_resize<Container, false> {
75 using segment_vector_type = Container;
78 resize(segment_vector_type &c,
size_t n)
83 template <
template <
typename>
class SegmentVectorType,
84 template <
typename>
class SegmentType,
size_t SegmentSize>
85 class fixed_size_policy {
89 using segment_vector_type = SegmentVectorType<SegmentType<T>>;
92 using segment_type = SegmentType<T>;
95 using value_type =
typename segment_type<T>::value_type;
97 using size_type = std::size_t;
100 using segment_vector_resize_type =
101 segment_vector_resize<segment_vector_type<T>>;
103 static constexpr size_type Size = SegmentSize;
105 template <
typename T>
107 resize(segment_vector_type<T> &c, size_type n)
109 segment_vector_resize_type<T>::resize(c, n);
118 get_segment(size_type index)
128 segment_top(size_type segment_index)
130 return segment_index * Size;
138 segment_size(size_type segment_index)
148 index_in_segment(size_type index)
156 template <
typename T>
158 max_size(
const segment_vector_type<T> &seg_storage)
160 return seg_storage.max_size() * SegmentSize;
167 capacity(size_type segment_index)
169 return (segment_index + 1) * Size;
173 template <
template <
typename>
class SegmentVectorType,
174 template <
typename>
class SegmentType>
175 class exponential_size_policy {
178 template <
typename T>
179 using segment_vector_type = SegmentVectorType<SegmentType<T>>;
181 template <
typename T>
182 using segment_type = SegmentType<T>;
184 template <
typename T>
185 using value_type =
typename segment_type<T>::value_type;
187 using size_type = std::size_t;
189 template <
typename T>
190 using segment_vector_resize_type =
191 segment_vector_resize<segment_vector_type<T>>;
193 template <
typename T>
195 resize(segment_vector_type<T> &c, size_type n)
197 segment_vector_resize_type<T>::resize(c, n);
206 get_segment(size_type index)
208 return static_cast<size_type
>(detail::Log2(index | 1));
216 segment_top(size_type segment_index)
218 return (size_type(1) << segment_index) & ~size_type(1);
226 segment_size(size_type segment_index)
228 return (segment_index == 0) ? 2 : segment_top(segment_index);
236 index_in_segment(size_type index)
238 return index - segment_top(get_segment(index));
244 template <
typename T>
246 max_size(
const segment_vector_type<T> &)
248 return segment_size(get_segment(PMEMOBJ_MAX_ALLOC_SIZE /
249 sizeof(value_type<T>)) +
257 capacity(size_type segment_index)
259 if (segment_index == 0)
261 return segment_size(segment_index) * 2;