1 //===----------------------------------------------------------------------===// 2 // 3 // The LLVM Compiler Infrastructure 4 // 5 // This file is dual licensed under the MIT and the University of Illinois Open 6 // Source Licenses. See LICENSE.TXT for details. 7 // 8 //===----------------------------------------------------------------------===// 9 10 #ifndef ALLOCATORS_H 11 #define ALLOCATORS_H 12 13 #include <type_traits> 14 #include <utility> 15 16 #include "test_macros.h" 17 18 #if TEST_STD_VER >= 11 19 20 template <class T> 21 class A1 22 { 23 int id_; 24 public: id_(id)25 explicit A1(int id = 0) TEST_NOEXCEPT : id_(id) {} 26 27 typedef T value_type; 28 id()29 int id() const {return id_;} 30 31 static bool copy_called; 32 static bool move_called; 33 static bool allocate_called; 34 static std::pair<T*, std::size_t> deallocate_called; 35 A1(const A1 & a)36 A1(const A1& a) TEST_NOEXCEPT : id_(a.id()) {copy_called = true;} A1(A1 && a)37 A1(A1&& a) TEST_NOEXCEPT : id_(a.id()) {move_called = true;} 38 A1& operator=(const A1& a) TEST_NOEXCEPT { id_ = a.id(); copy_called = true; return *this;} 39 A1& operator=(A1&& a) TEST_NOEXCEPT { id_ = a.id(); move_called = true; return *this;} 40 41 template <class U> A1(const A1<U> & a)42 A1(const A1<U>& a) TEST_NOEXCEPT : id_(a.id()) {copy_called = true;} 43 template <class U> A1(A1<U> && a)44 A1(A1<U>&& a) TEST_NOEXCEPT : id_(a.id()) {move_called = true;} 45 allocate(std::size_t n)46 T* allocate(std::size_t n) 47 { 48 allocate_called = true; 49 return (T*)n; 50 } 51 deallocate(T * p,std::size_t n)52 void deallocate(T* p, std::size_t n) 53 { 54 deallocate_called = std::pair<T*, std::size_t>(p, n); 55 } 56 max_size()57 std::size_t max_size() const {return id_;} 58 }; 59 60 template <class T> bool A1<T>::copy_called = false; 61 template <class T> bool A1<T>::move_called = false; 62 template <class T> bool A1<T>::allocate_called = false; 63 template <class T> std::pair<T*, std::size_t> A1<T>::deallocate_called; 64 65 template <class T, class U> 66 inline 67 bool operator==(const A1<T>& x, const A1<U>& y) 68 { 69 return x.id() == y.id(); 70 } 71 72 template <class T, class U> 73 inline 74 bool operator!=(const A1<T>& x, const A1<U>& y) 75 { 76 return !(x == y); 77 } 78 79 template <class T> 80 class A2 81 { 82 int id_; 83 public: id_(id)84 explicit A2(int id = 0) TEST_NOEXCEPT : id_(id) {} 85 86 typedef T value_type; 87 88 typedef unsigned size_type; 89 typedef int difference_type; 90 91 typedef std::true_type propagate_on_container_move_assignment; 92 id()93 int id() const {return id_;} 94 95 static bool copy_called; 96 static bool move_called; 97 static bool allocate_called; 98 A2(const A2 & a)99 A2(const A2& a) TEST_NOEXCEPT : id_(a.id()) {copy_called = true;} A2(A2 && a)100 A2(A2&& a) TEST_NOEXCEPT : id_(a.id()) {move_called = true;} 101 A2& operator=(const A2& a) TEST_NOEXCEPT { id_ = a.id(); copy_called = true; return *this;} 102 A2& operator=(A2&& a) TEST_NOEXCEPT { id_ = a.id(); move_called = true; return *this;} 103 allocate(std::size_t,const void * hint)104 T* allocate(std::size_t, const void* hint) 105 { 106 allocate_called = true; 107 return (T*) const_cast<void *>(hint); 108 } 109 }; 110 111 template <class T> bool A2<T>::copy_called = false; 112 template <class T> bool A2<T>::move_called = false; 113 template <class T> bool A2<T>::allocate_called = false; 114 115 template <class T, class U> 116 inline 117 bool operator==(const A2<T>& x, const A2<U>& y) 118 { 119 return x.id() == y.id(); 120 } 121 122 template <class T, class U> 123 inline 124 bool operator!=(const A2<T>& x, const A2<U>& y) 125 { 126 return !(x == y); 127 } 128 129 template <class T> 130 class A3 131 { 132 int id_; 133 public: id_(id)134 explicit A3(int id = 0) TEST_NOEXCEPT : id_(id) {} 135 136 typedef T value_type; 137 138 typedef std::true_type propagate_on_container_copy_assignment; 139 typedef std::true_type propagate_on_container_swap; 140 id()141 int id() const {return id_;} 142 143 static bool copy_called; 144 static bool move_called; 145 static bool constructed; 146 static bool destroy_called; 147 A3(const A3 & a)148 A3(const A3& a) TEST_NOEXCEPT : id_(a.id()) {copy_called = true;} A3(A3 && a)149 A3(A3&& a) TEST_NOEXCEPT : id_(a.id()) {move_called = true;} 150 A3& operator=(const A3& a) TEST_NOEXCEPT { id_ = a.id(); copy_called = true; return *this;} 151 A3& operator=(A3&& a) TEST_NOEXCEPT { id_ = a.id(); move_called = true; return *this;} 152 153 template <class U, class ...Args> construct(U * p,Args &&...args)154 void construct(U* p, Args&& ...args) 155 { 156 ::new (p) U(std::forward<Args>(args)...); 157 constructed = true; 158 } 159 160 template <class U> destroy(U * p)161 void destroy(U* p) 162 { 163 p->~U(); 164 destroy_called = true; 165 } 166 select_on_container_copy_construction()167 A3 select_on_container_copy_construction() const {return A3(-1);} 168 }; 169 170 template <class T> bool A3<T>::copy_called = false; 171 template <class T> bool A3<T>::move_called = false; 172 template <class T> bool A3<T>::constructed = false; 173 template <class T> bool A3<T>::destroy_called = false; 174 175 template <class T, class U> 176 inline 177 bool operator==(const A3<T>& x, const A3<U>& y) 178 { 179 return x.id() == y.id(); 180 } 181 182 template <class T, class U> 183 inline 184 bool operator!=(const A3<T>& x, const A3<U>& y) 185 { 186 return !(x == y); 187 } 188 189 #endif // TEST_STD_VER >= 11 190 191 #endif // ALLOCATORS_H 192