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 MIN_ALLOCATOR_H 11 #define MIN_ALLOCATOR_H 12 13 #include <cstddef> 14 15 template <class T> 16 class bare_allocator 17 { 18 public: 19 typedef T value_type; 20 bare_allocator()21 bare_allocator() {} 22 23 template <class U> bare_allocator(bare_allocator<U>)24 bare_allocator(bare_allocator<U>) {} 25 allocate(std::size_t n)26 T* allocate(std::size_t n) 27 { 28 return static_cast<T*>(::operator new(n*sizeof(T))); 29 } 30 deallocate(T * p,std::size_t)31 void deallocate(T* p, std::size_t) 32 { 33 return ::operator delete(static_cast<void*>(p)); 34 } 35 36 friend bool operator==(bare_allocator, bare_allocator) {return true;} 37 friend bool operator!=(bare_allocator x, bare_allocator y) {return !(x == y);} 38 }; 39 40 41 #if __cplusplus >= 201103L 42 43 #include <memory> 44 45 template <class T> class min_pointer; 46 template <class T> class min_pointer<const T>; 47 template <> class min_pointer<void>; 48 template <> class min_pointer<const void>; 49 template <class T> class min_allocator; 50 51 template <> 52 class min_pointer<const void> 53 { 54 const void* ptr_; 55 public: 56 min_pointer() noexcept = default; min_pointer(std::nullptr_t)57 min_pointer(std::nullptr_t) : ptr_(nullptr) {} 58 template <class T> min_pointer(min_pointer<T> p)59 min_pointer(min_pointer<T> p) : ptr_(p.ptr_) {} 60 61 explicit operator bool() const {return ptr_ != nullptr;} 62 63 friend bool operator==(min_pointer x, min_pointer y) {return x.ptr_ == y.ptr_;} 64 friend bool operator!=(min_pointer x, min_pointer y) {return !(x == y);} 65 template <class U> friend class min_pointer; 66 }; 67 68 template <> 69 class min_pointer<void> 70 { 71 void* ptr_; 72 public: 73 min_pointer() noexcept = default; min_pointer(std::nullptr_t)74 min_pointer(std::nullptr_t) : ptr_(nullptr) {} 75 template <class T, 76 class = typename std::enable_if 77 < 78 !std::is_const<T>::value 79 >::type 80 > min_pointer(min_pointer<T> p)81 min_pointer(min_pointer<T> p) : ptr_(p.ptr_) {} 82 83 explicit operator bool() const {return ptr_ != nullptr;} 84 85 friend bool operator==(min_pointer x, min_pointer y) {return x.ptr_ == y.ptr_;} 86 friend bool operator!=(min_pointer x, min_pointer y) {return !(x == y);} 87 template <class U> friend class min_pointer; 88 }; 89 90 template <class T> 91 class min_pointer 92 { 93 T* ptr_; 94 min_pointer(T * p)95 explicit min_pointer(T* p) : ptr_(p) {} 96 public: 97 min_pointer() noexcept = default; min_pointer(std::nullptr_t)98 min_pointer(std::nullptr_t) : ptr_(nullptr) {} min_pointer(min_pointer<void> p)99 explicit min_pointer(min_pointer<void> p) : ptr_(static_cast<T*>(p.ptr_)) {} 100 101 explicit operator bool() const {return ptr_ != nullptr;} 102 103 typedef std::ptrdiff_t difference_type; 104 typedef T& reference; 105 typedef T* pointer; 106 typedef T value_type; 107 typedef std::random_access_iterator_tag iterator_category; 108 109 reference operator*() const {return *ptr_;} 110 pointer operator->() const {return ptr_;} 111 112 min_pointer& operator++() {++ptr_; return *this;} 113 min_pointer operator++(int) {min_pointer tmp(*this); ++ptr_; return tmp;} 114 115 min_pointer& operator--() {--ptr_; return *this;} 116 min_pointer operator--(int) {min_pointer tmp(*this); --ptr_; return tmp;} 117 118 min_pointer& operator+=(difference_type n) {ptr_ += n; return *this;} 119 min_pointer& operator-=(difference_type n) {ptr_ -= n; return *this;} 120 121 min_pointer operator+(difference_type n) const 122 { 123 min_pointer tmp(*this); 124 tmp += n; 125 return tmp; 126 } 127 128 friend min_pointer operator+(difference_type n, min_pointer x) 129 { 130 return x + n; 131 } 132 133 min_pointer operator-(difference_type n) const 134 { 135 min_pointer tmp(*this); 136 tmp -= n; 137 return tmp; 138 } 139 140 friend difference_type operator-(min_pointer x, min_pointer y) 141 { 142 return x.ptr_ - y.ptr_; 143 } 144 145 reference operator[](difference_type n) const {return ptr_[n];} 146 147 friend bool operator< (min_pointer x, min_pointer y) {return x.ptr_ < y.ptr_;} 148 friend bool operator> (min_pointer x, min_pointer y) {return y < x;} 149 friend bool operator<=(min_pointer x, min_pointer y) {return !(y < x);} 150 friend bool operator>=(min_pointer x, min_pointer y) {return !(x < y);} 151 pointer_to(T & t)152 static min_pointer pointer_to(T& t) {return min_pointer(std::addressof(t));} 153 154 friend bool operator==(min_pointer x, min_pointer y) {return x.ptr_ == y.ptr_;} 155 friend bool operator!=(min_pointer x, min_pointer y) {return !(x == y);} 156 template <class U> friend class min_pointer; 157 template <class U> friend class min_allocator; 158 }; 159 160 template <class T> 161 class min_pointer<const T> 162 { 163 const T* ptr_; 164 min_pointer(const T * p)165 explicit min_pointer(const T* p) : ptr_(p) {} 166 public: 167 min_pointer() noexcept = default; min_pointer(std::nullptr_t)168 min_pointer(std::nullptr_t) : ptr_(nullptr) {} min_pointer(min_pointer<T> p)169 min_pointer(min_pointer<T> p) : ptr_(p.ptr_) {} min_pointer(min_pointer<const void> p)170 explicit min_pointer(min_pointer<const void> p) : ptr_(static_cast<const T*>(p.ptr_)) {} 171 172 explicit operator bool() const {return ptr_ != nullptr;} 173 174 typedef std::ptrdiff_t difference_type; 175 typedef const T& reference; 176 typedef const T* pointer; 177 typedef const T value_type; 178 typedef std::random_access_iterator_tag iterator_category; 179 180 reference operator*() const {return *ptr_;} 181 pointer operator->() const {return ptr_;} 182 183 min_pointer& operator++() {++ptr_; return *this;} 184 min_pointer operator++(int) {min_pointer tmp(*this); ++ptr_; return tmp;} 185 186 min_pointer& operator--() {--ptr_; return *this;} 187 min_pointer operator--(int) {min_pointer tmp(*this); --ptr_; return tmp;} 188 189 min_pointer& operator+=(difference_type n) {ptr_ += n; return *this;} 190 min_pointer& operator-=(difference_type n) {ptr_ -= n; return *this;} 191 192 min_pointer operator+(difference_type n) const 193 { 194 min_pointer tmp(*this); 195 tmp += n; 196 return tmp; 197 } 198 199 friend min_pointer operator+(difference_type n, min_pointer x) 200 { 201 return x + n; 202 } 203 204 min_pointer operator-(difference_type n) const 205 { 206 min_pointer tmp(*this); 207 tmp -= n; 208 return tmp; 209 } 210 211 friend difference_type operator-(min_pointer x, min_pointer y) 212 { 213 return x.ptr_ - y.ptr_; 214 } 215 216 reference operator[](difference_type n) const {return ptr_[n];} 217 218 friend bool operator< (min_pointer x, min_pointer y) {return x.ptr_ < y.ptr_;} 219 friend bool operator> (min_pointer x, min_pointer y) {return y < x;} 220 friend bool operator<=(min_pointer x, min_pointer y) {return !(y < x);} 221 friend bool operator>=(min_pointer x, min_pointer y) {return !(x < y);} 222 pointer_to(const T & t)223 static min_pointer pointer_to(const T& t) {return min_pointer(std::addressof(t));} 224 225 friend bool operator==(min_pointer x, min_pointer y) {return x.ptr_ == y.ptr_;} 226 friend bool operator!=(min_pointer x, min_pointer y) {return !(x == y);} 227 template <class U> friend class min_pointer; 228 }; 229 230 template <class T> 231 inline 232 bool 233 operator==(min_pointer<T> x, std::nullptr_t) 234 { 235 return !static_cast<bool>(x); 236 } 237 238 template <class T> 239 inline 240 bool 241 operator==(std::nullptr_t, min_pointer<T> x) 242 { 243 return !static_cast<bool>(x); 244 } 245 246 template <class T> 247 inline 248 bool 249 operator!=(min_pointer<T> x, std::nullptr_t) 250 { 251 return static_cast<bool>(x); 252 } 253 254 template <class T> 255 inline 256 bool 257 operator!=(std::nullptr_t, min_pointer<T> x) 258 { 259 return static_cast<bool>(x); 260 } 261 262 template <class T> 263 class min_allocator 264 { 265 public: 266 typedef T value_type; 267 typedef min_pointer<T> pointer; 268 269 min_allocator() = default; 270 template <class U> min_allocator(min_allocator<U>)271 min_allocator(min_allocator<U>) {} 272 allocate(std::ptrdiff_t n)273 pointer allocate(std::ptrdiff_t n) 274 { 275 return pointer(static_cast<T*>(::operator new(n*sizeof(T)))); 276 } 277 deallocate(pointer p,std::ptrdiff_t)278 void deallocate(pointer p, std::ptrdiff_t) 279 { 280 return ::operator delete(p.ptr_); 281 } 282 283 friend bool operator==(min_allocator, min_allocator) {return true;} 284 friend bool operator!=(min_allocator x, min_allocator y) {return !(x == y);} 285 }; 286 287 #endif // __cplusplus >= 201103L 288 289 #endif // MIN_ALLOCATOR_H 290