|
1 | 1 | #ifndef _LV_ALIGNED_ALLOCATOR_HPP |
2 | 2 | #define _LV_ALIGNED_ALLOCATOR_HPP |
3 | 3 |
|
4 | | -#include <cstddef> |
5 | | -#include <cstdlib> |
6 | | -#include <new> |
7 | 4 | #include <libvisual/lv_mem.h> |
| 5 | +#include <cstdlib> |
| 6 | +#include <limits> |
| 7 | +#include <memory> |
| 8 | +#include <stdexcept> |
8 | 9 |
|
9 | | -namespace LV { |
10 | | - |
11 | | - template <typename T, std::size_t alignment> |
12 | | - struct AlignedAllocator; |
13 | | - |
14 | | - template <std::size_t alignment> |
15 | | - struct AlignedAllocator<void, alignment> |
16 | | - { |
17 | | - typedef void value_type; |
18 | | - typedef void* pointer; |
19 | | - typedef void const* const_pointer; |
20 | | - |
21 | | - template <typename U> |
22 | | - struct rebind { typedef AlignedAllocator<U, alignment> other; }; |
23 | | - }; |
24 | | - |
| 10 | +namespace LV |
| 11 | +{ |
25 | 12 | //! Aligned memory allocator. |
26 | 13 | //! |
27 | | - //! @tparam T type of object to allocate |
28 | 14 | //! @tparam alignment alignment boundary |
| 15 | + //! @tparam T type of object to allocate |
29 | 16 | //! |
30 | 17 | //! AlignedAllocator is an implementation of the C++ Allocator concept for use with standard library containers. |
31 | 18 | //! |
32 | | - template <typename T, std::size_t alignment> |
| 19 | + template <std::size_t alignment, typename T = std::byte> |
33 | 20 | struct AlignedAllocator |
34 | 21 | { |
35 | | - typedef T* pointer; |
36 | | - typedef T& reference; |
37 | | - typedef T const* const_pointer; |
38 | | - typedef T const& const_reference; |
39 | | - typedef T value_type; |
40 | | - typedef std::size_t size_type; |
41 | | - typedef std::ptrdiff_t difference_type; |
| 22 | + using value_type = T; |
42 | 23 |
|
43 | | - template <typename U> |
44 | | - struct rebind { typedef AlignedAllocator<U, alignment> other; }; |
45 | | - |
46 | | - AlignedAllocator () |
47 | | - {} |
| 24 | + AlignedAllocator () = default; |
48 | 25 |
|
49 | 26 | template <typename U> |
50 | | - AlignedAllocator (AlignedAllocator<U, alignment>&) |
| 27 | + constexpr AlignedAllocator (AlignedAllocator<alignment, U> const&) noexcept |
51 | 28 | {} |
52 | 29 |
|
53 | | - pointer address (reference x) const |
| 30 | + [[nodiscard]] T* allocate (std::size_t n) |
54 | 31 | { |
55 | | - return &x; |
56 | | - } |
| 32 | + if (n > std::numeric_limits<std::size_t>::max () / sizeof (T)) |
| 33 | + throw std::bad_array_new_length {}; |
57 | 34 |
|
58 | | - const_pointer address (const_reference x) const |
59 | | - { |
60 | | - return &x; |
61 | | - } |
62 | | - |
63 | | - pointer allocate (size_type n, typename AlignedAllocator<void, alignment>::pointer = nullptr) |
64 | | - { |
65 | | - void* ptr = visual_mem_malloc_aligned (n * sizeof (T), alignment); |
| 35 | + auto ptr = visual_mem_malloc_aligned (n * sizeof (T), alignment); |
66 | 36 |
|
67 | 37 | if (!ptr) |
68 | | - throw std::bad_alloc (); |
| 38 | + throw std::bad_alloc {}; |
69 | 39 |
|
70 | | - return pointer (ptr); |
| 40 | + return ptr; |
71 | 41 | } |
72 | 42 |
|
73 | | - void deallocate (pointer ptr, size_type) noexcept |
| 43 | + void deallocate (T* ptr, std::size_t) noexcept |
74 | 44 | { |
75 | 45 | visual_mem_free_aligned (ptr); |
76 | 46 | } |
77 | | - |
78 | | - size_type max_size () const |
79 | | - { |
80 | | - return size_type (-1) / sizeof (T); |
81 | | - } |
82 | | - |
83 | | - void construct (pointer p, const_reference x) |
84 | | - { |
85 | | - new (p) T (x); |
86 | | - } |
87 | | - |
88 | | - void destroy (pointer p) |
89 | | - { |
90 | | - p->~T (); |
91 | | - } |
92 | 47 | }; |
93 | 48 |
|
94 | 49 | template <typename T, typename U, std::size_t alignment> |
95 | | - bool operator== (AlignedAllocator<T, alignment> const&, AlignedAllocator<U, alignment> const&) |
| 50 | + bool operator== (AlignedAllocator<alignment, T> const&, AlignedAllocator<alignment, U> const&) |
96 | 51 | { |
97 | 52 | return true; |
98 | 53 | } |
99 | 54 |
|
100 | 55 | template <typename T, typename U, std::size_t alignment> |
101 | | - bool operator!= (AlignedAllocator<T, alignment> const&, AlignedAllocator<U, alignment> const&) |
| 56 | + bool operator!= (AlignedAllocator<alignment, T> const&, AlignedAllocator<alignment, U> const&) |
102 | 57 | { |
103 | 58 | return false; |
104 | 59 | } |
|
0 commit comments