1 //===- llvm/ADT/SmallVector.h - 'Normally small' vectors --------*- C++ -*-===// 2 // 3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. 4 // See https://llvm.org/LICENSE.txt for license information. 5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception 6 // 7 //===----------------------------------------------------------------------===// 8 /// 9 /// \file 10 /// This file defines the SmallVector class. 11 /// 12 //===----------------------------------------------------------------------===// 13 14 #ifndef LLVM_ADT_SMALLVECTOR_H 15 #define LLVM_ADT_SMALLVECTOR_H 16 17 #include "llvm/Support/Compiler.h" 18 #include <algorithm> 19 #include <cassert> 20 #include <cstddef> 21 #include <cstdint> 22 #include <cstdlib> 23 #include <cstring> 24 #include <functional> 25 #include <initializer_list> 26 #include <iterator> 27 #include <limits> 28 #include <memory> 29 #include <new> 30 #include <type_traits> 31 #include <utility> 32 33 namespace llvm { 34 35 template <typename T> class ArrayRef; 36 37 template <typename IteratorT> class iterator_range; 38 39 template <class Iterator> 40 using EnableIfConvertibleToInputIterator = std::enable_if_t<std::is_convertible< 41 typename std::iterator_traits<Iterator>::iterator_category, 42 std::input_iterator_tag>::value>; 43 44 /// This is all the stuff common to all SmallVectors. 45 /// 46 /// The template parameter specifies the type which should be used to hold the 47 /// Size and Capacity of the SmallVector, so it can be adjusted. 48 /// Using 32 bit size is desirable to shrink the size of the SmallVector. 49 /// Using 64 bit size is desirable for cases like SmallVector<char>, where a 50 /// 32 bit size would limit the vector to ~4GB. SmallVectors are used for 51 /// buffering bitcode output - which can exceed 4GB. 52 template <class Size_T> class SmallVectorBase { 53 protected: 54 void *BeginX; 55 Size_T Size = 0, Capacity; 56 57 /// The maximum value of the Size_T used. 58 static constexpr size_t SizeTypeMax() { 59 return std::numeric_limits<Size_T>::max(); 60 } 61 62 SmallVectorBase() = delete; 63 SmallVectorBase(void *FirstEl, size_t TotalCapacity) 64 : BeginX(FirstEl), Capacity(static_cast<Size_T>(TotalCapacity)) {} 65 66 /// This is a helper for \a grow() that's out of line to reduce code 67 /// duplication. This function will report a fatal error if it can't grow at 68 /// least to \p MinSize. 69 void *mallocForGrow(void *FirstEl, size_t MinSize, size_t TSize, 70 size_t &NewCapacity); 71 72 /// This is an implementation of the grow() method which only works 73 /// on POD-like data types and is out of line to reduce code duplication. 74 /// This function will report a fatal error if it cannot increase capacity. 75 void grow_pod(void *FirstEl, size_t MinSize, size_t TSize); 76 77 public: 78 size_t size() const { return Size; } 79 size_t capacity() const { return Capacity; } 80 81 [[nodiscard]] bool empty() const { return !Size; } 82 83 protected: 84 /// Set the array size to \p N, which the current array must have enough 85 /// capacity for. 86 /// 87 /// This does not construct or destroy any elements in the vector. 88 void set_size(size_t N) { 89 assert(N <= capacity()); // implies no overflow in assignment 90 Size = static_cast<Size_T>(N); 91 } 92 93 /// Set the array data pointer to \p Begin and capacity to \p N. 94 /// 95 /// This does not construct or destroy any elements in the vector. 96 // This does not clean up any existing allocation. 97 void set_allocation_range(void *Begin, size_t N) { 98 assert(N <= SizeTypeMax()); 99 BeginX = Begin; 100 Capacity = static_cast<Size_T>(N); 101 } 102 }; 103 104 template <class T> 105 using SmallVectorSizeType = 106 std::conditional_t<sizeof(T) < 4 && sizeof(void *) >= 8, uint64_t, 107 uint32_t>; 108 109 /// Figure out the offset of the first element. 110 template <class T, typename = void> struct SmallVectorAlignmentAndSize { 111 alignas(SmallVectorBase<SmallVectorSizeType<T>>) char Base[sizeof( 112 SmallVectorBase<SmallVectorSizeType<T>>)]; 113 alignas(T) char FirstEl[sizeof(T)]; 114 }; 115 116 /// This is the part of SmallVectorTemplateBase which does not depend on whether 117 /// the type T is a POD. The extra dummy template argument is used by ArrayRef 118 /// to avoid unnecessarily requiring T to be complete. 119 template <typename T, typename = void> 120 class SmallVectorTemplateCommon 121 : public SmallVectorBase<SmallVectorSizeType<T>> { 122 using Base = SmallVectorBase<SmallVectorSizeType<T>>; 123 124 protected: 125 /// Find the address of the first element. For this pointer math to be valid 126 /// with small-size of 0 for T with lots of alignment, it's important that 127 /// SmallVectorStorage is properly-aligned even for small-size of 0. 128 void *getFirstEl() const { 129 return const_cast<void *>(reinterpret_cast<const void *>( 130 reinterpret_cast<const char *>(this) + 131 offsetof(SmallVectorAlignmentAndSize<T>, FirstEl))); 132 } 133 // Space after 'FirstEl' is clobbered, do not add any instance vars after it. 134 135 SmallVectorTemplateCommon(size_t Size) : Base(getFirstEl(), Size) {} 136 137 void grow_pod(size_t MinSize, size_t TSize) { 138 Base::grow_pod(getFirstEl(), MinSize, TSize); 139 } 140 141 /// Return true if this is a smallvector which has not had dynamic 142 /// memory allocated for it. 143 bool isSmall() const { return this->BeginX == getFirstEl(); } 144 145 /// Put this vector in a state of being small. 146 void resetToSmall() { 147 this->BeginX = getFirstEl(); 148 this->Size = this->Capacity = 0; // FIXME: Setting Capacity to 0 is suspect. 149 } 150 151 /// Return true if V is an internal reference to the given range. 152 bool isReferenceToRange(const void *V, const void *First, const void *Last) const { 153 // Use std::less to avoid UB. 154 std::less<> LessThan; 155 return !LessThan(V, First) && LessThan(V, Last); 156 } 157 158 /// Return true if V is an internal reference to this vector. 159 bool isReferenceToStorage(const void *V) const { 160 return isReferenceToRange(V, this->begin(), this->end()); 161 } 162 163 /// Return true if First and Last form a valid (possibly empty) range in this 164 /// vector's storage. 165 bool isRangeInStorage(const void *First, const void *Last) const { 166 // Use std::less to avoid UB. 167 std::less<> LessThan; 168 return !LessThan(First, this->begin()) && !LessThan(Last, First) && 169 !LessThan(this->end(), Last); 170 } 171 172 /// Return true unless Elt will be invalidated by resizing the vector to 173 /// NewSize. 174 bool isSafeToReferenceAfterResize(const void *Elt, size_t NewSize) { 175 // Past the end. 176 if (LLVM_LIKELY(!isReferenceToStorage(Elt))) 177 return true; 178 179 // Return false if Elt will be destroyed by shrinking. 180 if (NewSize <= this->size()) 181 return Elt < this->begin() + NewSize; 182 183 // Return false if we need to grow. 184 return NewSize <= this->capacity(); 185 } 186 187 /// Check whether Elt will be invalidated by resizing the vector to NewSize. 188 void assertSafeToReferenceAfterResize(const void *Elt, size_t NewSize) { 189 assert(isSafeToReferenceAfterResize(Elt, NewSize) && 190 "Attempting to reference an element of the vector in an operation " 191 "that invalidates it"); 192 } 193 194 /// Check whether Elt will be invalidated by increasing the size of the 195 /// vector by N. 196 void assertSafeToAdd(const void *Elt, size_t N = 1) { 197 this->assertSafeToReferenceAfterResize(Elt, this->size() + N); 198 } 199 200 /// Check whether any part of the range will be invalidated by clearing. 201 void assertSafeToReferenceAfterClear(const T *From, const T *To) { 202 if (From == To) 203 return; 204 this->assertSafeToReferenceAfterResize(From, 0); 205 this->assertSafeToReferenceAfterResize(To - 1, 0); 206 } 207 template < 208 class ItTy, 209 std::enable_if_t<!std::is_same<std::remove_const_t<ItTy>, T *>::value, 210 bool> = false> 211 void assertSafeToReferenceAfterClear(ItTy, ItTy) {} 212 213 /// Check whether any part of the range will be invalidated by growing. 214 void assertSafeToAddRange(const T *From, const T *To) { 215 if (From == To) 216 return; 217 this->assertSafeToAdd(From, To - From); 218 this->assertSafeToAdd(To - 1, To - From); 219 } 220 template < 221 class ItTy, 222 std::enable_if_t<!std::is_same<std::remove_const_t<ItTy>, T *>::value, 223 bool> = false> 224 void assertSafeToAddRange(ItTy, ItTy) {} 225 226 /// Reserve enough space to add one element, and return the updated element 227 /// pointer in case it was a reference to the storage. 228 template <class U> 229 static const T *reserveForParamAndGetAddressImpl(U *This, const T &Elt, 230 size_t N) { 231 size_t NewSize = This->size() + N; 232 if (LLVM_LIKELY(NewSize <= This->capacity())) 233 return &Elt; 234 235 bool ReferencesStorage = false; 236 int64_t Index = -1; 237 if (!U::TakesParamByValue) { 238 if (LLVM_UNLIKELY(This->isReferenceToStorage(&Elt))) { 239 ReferencesStorage = true; 240 Index = &Elt - This->begin(); 241 } 242 } 243 This->grow(NewSize); 244 return ReferencesStorage ? This->begin() + Index : &Elt; 245 } 246 247 public: 248 using size_type = size_t; 249 using difference_type = ptrdiff_t; 250 using value_type = T; 251 using iterator = T *; 252 using const_iterator = const T *; 253 254 using const_reverse_iterator = std::reverse_iterator<const_iterator>; 255 using reverse_iterator = std::reverse_iterator<iterator>; 256 257 using reference = T &; 258 using const_reference = const T &; 259 using pointer = T *; 260 using const_pointer = const T *; 261 262 using Base::capacity; 263 using Base::empty; 264 using Base::size; 265 266 // forward iterator creation methods. 267 iterator begin() { return (iterator)this->BeginX; } 268 const_iterator begin() const { return (const_iterator)this->BeginX; } 269 iterator end() { return begin() + size(); } 270 const_iterator end() const { return begin() + size(); } 271 272 // reverse iterator creation methods. 273 reverse_iterator rbegin() { return reverse_iterator(end()); } 274 const_reverse_iterator rbegin() const{ return const_reverse_iterator(end()); } 275 reverse_iterator rend() { return reverse_iterator(begin()); } 276 const_reverse_iterator rend() const { return const_reverse_iterator(begin());} 277 278 size_type size_in_bytes() const { return size() * sizeof(T); } 279 size_type max_size() const { 280 return std::min(this->SizeTypeMax(), size_type(-1) / sizeof(T)); 281 } 282 283 size_t capacity_in_bytes() const { return capacity() * sizeof(T); } 284 285 /// Return a pointer to the vector's buffer, even if empty(). 286 pointer data() { return pointer(begin()); } 287 /// Return a pointer to the vector's buffer, even if empty(). 288 const_pointer data() const { return const_pointer(begin()); } 289 290 reference operator[](size_type idx) { 291 assert(idx < size()); 292 return begin()[idx]; 293 } 294 const_reference operator[](size_type idx) const { 295 assert(idx < size()); 296 return begin()[idx]; 297 } 298 299 reference front() { 300 assert(!empty()); 301 return begin()[0]; 302 } 303 const_reference front() const { 304 assert(!empty()); 305 return begin()[0]; 306 } 307 308 reference back() { 309 assert(!empty()); 310 return end()[-1]; 311 } 312 const_reference back() const { 313 assert(!empty()); 314 return end()[-1]; 315 } 316 }; 317 318 /// SmallVectorTemplateBase<TriviallyCopyable = false> - This is where we put 319 /// method implementations that are designed to work with non-trivial T's. 320 /// 321 /// We approximate is_trivially_copyable with trivial move/copy construction and 322 /// trivial destruction. While the standard doesn't specify that you're allowed 323 /// copy these types with memcpy, there is no way for the type to observe this. 324 /// This catches the important case of std::pair<POD, POD>, which is not 325 /// trivially assignable. 326 template <typename T, bool = (std::is_trivially_copy_constructible<T>::value) && 327 (std::is_trivially_move_constructible<T>::value) && 328 std::is_trivially_destructible<T>::value> 329 class SmallVectorTemplateBase : public SmallVectorTemplateCommon<T> { 330 friend class SmallVectorTemplateCommon<T>; 331 332 protected: 333 static constexpr bool TakesParamByValue = false; 334 using ValueParamT = const T &; 335 336 SmallVectorTemplateBase(size_t Size) : SmallVectorTemplateCommon<T>(Size) {} 337 338 static void destroy_range(T *S, T *E) { 339 while (S != E) { 340 --E; 341 E->~T(); 342 } 343 } 344 345 /// Move the range [I, E) into the uninitialized memory starting with "Dest", 346 /// constructing elements as needed. 347 template<typename It1, typename It2> 348 static void uninitialized_move(It1 I, It1 E, It2 Dest) { 349 std::uninitialized_move(I, E, Dest); 350 } 351 352 /// Copy the range [I, E) onto the uninitialized memory starting with "Dest", 353 /// constructing elements as needed. 354 template<typename It1, typename It2> 355 static void uninitialized_copy(It1 I, It1 E, It2 Dest) { 356 std::uninitialized_copy(I, E, Dest); 357 } 358 359 /// Grow the allocated memory (without initializing new elements), doubling 360 /// the size of the allocated memory. Guarantees space for at least one more 361 /// element, or MinSize more elements if specified. 362 void grow(size_t MinSize = 0); 363 364 /// Create a new allocation big enough for \p MinSize and pass back its size 365 /// in \p NewCapacity. This is the first section of \a grow(). 366 T *mallocForGrow(size_t MinSize, size_t &NewCapacity); 367 368 /// Move existing elements over to the new allocation \p NewElts, the middle 369 /// section of \a grow(). 370 void moveElementsForGrow(T *NewElts); 371 372 /// Transfer ownership of the allocation, finishing up \a grow(). 373 void takeAllocationForGrow(T *NewElts, size_t NewCapacity); 374 375 /// Reserve enough space to add one element, and return the updated element 376 /// pointer in case it was a reference to the storage. 377 const T *reserveForParamAndGetAddress(const T &Elt, size_t N = 1) { 378 return this->reserveForParamAndGetAddressImpl(this, Elt, N); 379 } 380 381 /// Reserve enough space to add one element, and return the updated element 382 /// pointer in case it was a reference to the storage. 383 T *reserveForParamAndGetAddress(T &Elt, size_t N = 1) { 384 return const_cast<T *>( 385 this->reserveForParamAndGetAddressImpl(this, Elt, N)); 386 } 387 388 static T &&forward_value_param(T &&V) { return std::move(V); } 389 static const T &forward_value_param(const T &V) { return V; } 390 391 void growAndAssign(size_t NumElts, const T &Elt) { 392 // Grow manually in case Elt is an internal reference. 393 size_t NewCapacity; 394 T *NewElts = mallocForGrow(NumElts, NewCapacity); 395 std::uninitialized_fill_n(NewElts, NumElts, Elt); 396 this->destroy_range(this->begin(), this->end()); 397 takeAllocationForGrow(NewElts, NewCapacity); 398 this->set_size(NumElts); 399 } 400 401 template <typename... ArgTypes> T &growAndEmplaceBack(ArgTypes &&... Args) { 402 // Grow manually in case one of Args is an internal reference. 403 size_t NewCapacity; 404 T *NewElts = mallocForGrow(0, NewCapacity); 405 ::new ((void *)(NewElts + this->size())) T(std::forward<ArgTypes>(Args)...); 406 moveElementsForGrow(NewElts); 407 takeAllocationForGrow(NewElts, NewCapacity); 408 this->set_size(this->size() + 1); 409 return this->back(); 410 } 411 412 public: 413 void push_back(const T &Elt) { 414 const T *EltPtr = reserveForParamAndGetAddress(Elt); 415 ::new ((void *)this->end()) T(*EltPtr); 416 this->set_size(this->size() + 1); 417 } 418 419 void push_back(T &&Elt) { 420 T *EltPtr = reserveForParamAndGetAddress(Elt); 421 ::new ((void *)this->end()) T(::std::move(*EltPtr)); 422 this->set_size(this->size() + 1); 423 } 424 425 void pop_back() { 426 this->set_size(this->size() - 1); 427 this->end()->~T(); 428 } 429 }; 430 431 // Define this out-of-line to dissuade the C++ compiler from inlining it. 432 template <typename T, bool TriviallyCopyable> 433 void SmallVectorTemplateBase<T, TriviallyCopyable>::grow(size_t MinSize) { 434 size_t NewCapacity; 435 T *NewElts = mallocForGrow(MinSize, NewCapacity); 436 moveElementsForGrow(NewElts); 437 takeAllocationForGrow(NewElts, NewCapacity); 438 } 439 440 template <typename T, bool TriviallyCopyable> 441 T *SmallVectorTemplateBase<T, TriviallyCopyable>::mallocForGrow( 442 size_t MinSize, size_t &NewCapacity) { 443 return static_cast<T *>( 444 SmallVectorBase<SmallVectorSizeType<T>>::mallocForGrow( 445 this->getFirstEl(), MinSize, sizeof(T), NewCapacity)); 446 } 447 448 // Define this out-of-line to dissuade the C++ compiler from inlining it. 449 template <typename T, bool TriviallyCopyable> 450 void SmallVectorTemplateBase<T, TriviallyCopyable>::moveElementsForGrow( 451 T *NewElts) { 452 // Move the elements over. 453 this->uninitialized_move(this->begin(), this->end(), NewElts); 454 455 // Destroy the original elements. 456 destroy_range(this->begin(), this->end()); 457 } 458 459 // Define this out-of-line to dissuade the C++ compiler from inlining it. 460 template <typename T, bool TriviallyCopyable> 461 void SmallVectorTemplateBase<T, TriviallyCopyable>::takeAllocationForGrow( 462 T *NewElts, size_t NewCapacity) { 463 // If this wasn't grown from the inline copy, deallocate the old space. 464 if (!this->isSmall()) 465 free(this->begin()); 466 467 this->set_allocation_range(NewElts, NewCapacity); 468 } 469 470 /// SmallVectorTemplateBase<TriviallyCopyable = true> - This is where we put 471 /// method implementations that are designed to work with trivially copyable 472 /// T's. This allows using memcpy in place of copy/move construction and 473 /// skipping destruction. 474 template <typename T> 475 class SmallVectorTemplateBase<T, true> : public SmallVectorTemplateCommon<T> { 476 friend class SmallVectorTemplateCommon<T>; 477 478 protected: 479 /// True if it's cheap enough to take parameters by value. Doing so avoids 480 /// overhead related to mitigations for reference invalidation. 481 static constexpr bool TakesParamByValue = sizeof(T) <= 2 * sizeof(void *); 482 483 /// Either const T& or T, depending on whether it's cheap enough to take 484 /// parameters by value. 485 using ValueParamT = std::conditional_t<TakesParamByValue, T, const T &>; 486 487 SmallVectorTemplateBase(size_t Size) : SmallVectorTemplateCommon<T>(Size) {} 488 489 // No need to do a destroy loop for POD's. 490 static void destroy_range(T *, T *) {} 491 492 /// Move the range [I, E) onto the uninitialized memory 493 /// starting with "Dest", constructing elements into it as needed. 494 template<typename It1, typename It2> 495 static void uninitialized_move(It1 I, It1 E, It2 Dest) { 496 // Just do a copy. 497 uninitialized_copy(I, E, Dest); 498 } 499 500 /// Copy the range [I, E) onto the uninitialized memory 501 /// starting with "Dest", constructing elements into it as needed. 502 template<typename It1, typename It2> 503 static void uninitialized_copy(It1 I, It1 E, It2 Dest) { 504 // Arbitrary iterator types; just use the basic implementation. 505 std::uninitialized_copy(I, E, Dest); 506 } 507 508 /// Copy the range [I, E) onto the uninitialized memory 509 /// starting with "Dest", constructing elements into it as needed. 510 template <typename T1, typename T2> 511 static void uninitialized_copy( 512 T1 *I, T1 *E, T2 *Dest, 513 std::enable_if_t<std::is_same<std::remove_const_t<T1>, T2>::value> * = 514 nullptr) { 515 // Use memcpy for PODs iterated by pointers (which includes SmallVector 516 // iterators): std::uninitialized_copy optimizes to memmove, but we can 517 // use memcpy here. Note that I and E are iterators and thus might be 518 // invalid for memcpy if they are equal. 519 if (I != E) 520 memcpy(reinterpret_cast<void *>(Dest), I, (E - I) * sizeof(T)); 521 } 522 523 /// Double the size of the allocated memory, guaranteeing space for at 524 /// least one more element or MinSize if specified. 525 void grow(size_t MinSize = 0) { this->grow_pod(MinSize, sizeof(T)); } 526 527 /// Reserve enough space to add one element, and return the updated element 528 /// pointer in case it was a reference to the storage. 529 const T *reserveForParamAndGetAddress(const T &Elt, size_t N = 1) { 530 return this->reserveForParamAndGetAddressImpl(this, Elt, N); 531 } 532 533 /// Reserve enough space to add one element, and return the updated element 534 /// pointer in case it was a reference to the storage. 535 T *reserveForParamAndGetAddress(T &Elt, size_t N = 1) { 536 return const_cast<T *>( 537 this->reserveForParamAndGetAddressImpl(this, Elt, N)); 538 } 539 540 /// Copy \p V or return a reference, depending on \a ValueParamT. 541 static ValueParamT forward_value_param(ValueParamT V) { return V; } 542 543 void growAndAssign(size_t NumElts, T Elt) { 544 // Elt has been copied in case it's an internal reference, side-stepping 545 // reference invalidation problems without losing the realloc optimization. 546 this->set_size(0); 547 this->grow(NumElts); 548 std::uninitialized_fill_n(this->begin(), NumElts, Elt); 549 this->set_size(NumElts); 550 } 551 552 template <typename... ArgTypes> T &growAndEmplaceBack(ArgTypes &&... Args) { 553 // Use push_back with a copy in case Args has an internal reference, 554 // side-stepping reference invalidation problems without losing the realloc 555 // optimization. 556 push_back(T(std::forward<ArgTypes>(Args)...)); 557 return this->back(); 558 } 559 560 public: 561 void push_back(ValueParamT Elt) { 562 const T *EltPtr = reserveForParamAndGetAddress(Elt); 563 memcpy(reinterpret_cast<void *>(this->end()), EltPtr, sizeof(T)); 564 this->set_size(this->size() + 1); 565 } 566 567 void pop_back() { this->set_size(this->size() - 1); } 568 }; 569 570 /// This class consists of common code factored out of the SmallVector class to 571 /// reduce code duplication based on the SmallVector 'N' template parameter. 572 template <typename T> 573 class SmallVectorImpl : public SmallVectorTemplateBase<T> { 574 using SuperClass = SmallVectorTemplateBase<T>; 575 576 public: 577 using iterator = typename SuperClass::iterator; 578 using const_iterator = typename SuperClass::const_iterator; 579 using reference = typename SuperClass::reference; 580 using size_type = typename SuperClass::size_type; 581 582 protected: 583 using SmallVectorTemplateBase<T>::TakesParamByValue; 584 using ValueParamT = typename SuperClass::ValueParamT; 585 586 // Default ctor - Initialize to empty. 587 explicit SmallVectorImpl(unsigned N) 588 : SmallVectorTemplateBase<T>(N) {} 589 590 void assignRemote(SmallVectorImpl &&RHS) { 591 this->destroy_range(this->begin(), this->end()); 592 if (!this->isSmall()) 593 free(this->begin()); 594 this->BeginX = RHS.BeginX; 595 this->Size = RHS.Size; 596 this->Capacity = RHS.Capacity; 597 RHS.resetToSmall(); 598 } 599 600 ~SmallVectorImpl() { 601 // Subclass has already destructed this vector's elements. 602 // If this wasn't grown from the inline copy, deallocate the old space. 603 if (!this->isSmall()) 604 free(this->begin()); 605 } 606 607 public: 608 SmallVectorImpl(const SmallVectorImpl &) = delete; 609 610 void clear() { 611 this->destroy_range(this->begin(), this->end()); 612 this->Size = 0; 613 } 614 615 private: 616 // Make set_size() private to avoid misuse in subclasses. 617 using SuperClass::set_size; 618 619 template <bool ForOverwrite> void resizeImpl(size_type N) { 620 if (N == this->size()) 621 return; 622 623 if (N < this->size()) { 624 this->truncate(N); 625 return; 626 } 627 628 this->reserve(N); 629 for (auto I = this->end(), E = this->begin() + N; I != E; ++I) 630 if (ForOverwrite) 631 new (&*I) T; 632 else 633 new (&*I) T(); 634 this->set_size(N); 635 } 636 637 public: 638 void resize(size_type N) { resizeImpl<false>(N); } 639 640 /// Like resize, but \ref T is POD, the new values won't be initialized. 641 void resize_for_overwrite(size_type N) { resizeImpl<true>(N); } 642 643 /// Like resize, but requires that \p N is less than \a size(). 644 void truncate(size_type N) { 645 assert(this->size() >= N && "Cannot increase size with truncate"); 646 this->destroy_range(this->begin() + N, this->end()); 647 this->set_size(N); 648 } 649 650 void resize(size_type N, ValueParamT NV) { 651 if (N == this->size()) 652 return; 653 654 if (N < this->size()) { 655 this->truncate(N); 656 return; 657 } 658 659 // N > this->size(). Defer to append. 660 this->append(N - this->size(), NV); 661 } 662 663 void reserve(size_type N) { 664 if (this->capacity() < N) 665 this->grow(N); 666 } 667 668 void pop_back_n(size_type NumItems) { 669 assert(this->size() >= NumItems); 670 truncate(this->size() - NumItems); 671 } 672 673 [[nodiscard]] T pop_back_val() { 674 T Result = ::std::move(this->back()); 675 this->pop_back(); 676 return Result; 677 } 678 679 void swap(SmallVectorImpl &RHS); 680 681 /// Add the specified range to the end of the SmallVector. 682 template <typename ItTy, typename = EnableIfConvertibleToInputIterator<ItTy>> 683 void append(ItTy in_start, ItTy in_end) { 684 this->assertSafeToAddRange(in_start, in_end); 685 size_type NumInputs = std::distance(in_start, in_end); 686 this->reserve(this->size() + NumInputs); 687 this->uninitialized_copy(in_start, in_end, this->end()); 688 this->set_size(this->size() + NumInputs); 689 } 690 691 /// Append \p NumInputs copies of \p Elt to the end. 692 void append(size_type NumInputs, ValueParamT Elt) { 693 const T *EltPtr = this->reserveForParamAndGetAddress(Elt, NumInputs); 694 std::uninitialized_fill_n(this->end(), NumInputs, *EltPtr); 695 this->set_size(this->size() + NumInputs); 696 } 697 698 void append(std::initializer_list<T> IL) { 699 append(IL.begin(), IL.end()); 700 } 701 702 void append(const SmallVectorImpl &RHS) { append(RHS.begin(), RHS.end()); } 703 704 void assign(size_type NumElts, ValueParamT Elt) { 705 // Note that Elt could be an internal reference. 706 if (NumElts > this->capacity()) { 707 this->growAndAssign(NumElts, Elt); 708 return; 709 } 710 711 // Assign over existing elements. 712 std::fill_n(this->begin(), std::min(NumElts, this->size()), Elt); 713 if (NumElts > this->size()) 714 std::uninitialized_fill_n(this->end(), NumElts - this->size(), Elt); 715 else if (NumElts < this->size()) 716 this->destroy_range(this->begin() + NumElts, this->end()); 717 this->set_size(NumElts); 718 } 719 720 // FIXME: Consider assigning over existing elements, rather than clearing & 721 // re-initializing them - for all assign(...) variants. 722 723 template <typename ItTy, typename = EnableIfConvertibleToInputIterator<ItTy>> 724 void assign(ItTy in_start, ItTy in_end) { 725 this->assertSafeToReferenceAfterClear(in_start, in_end); 726 clear(); 727 append(in_start, in_end); 728 } 729 730 void assign(std::initializer_list<T> IL) { 731 clear(); 732 append(IL); 733 } 734 735 void assign(const SmallVectorImpl &RHS) { assign(RHS.begin(), RHS.end()); } 736 737 iterator erase(const_iterator CI) { 738 // Just cast away constness because this is a non-const member function. 739 iterator I = const_cast<iterator>(CI); 740 741 assert(this->isReferenceToStorage(CI) && "Iterator to erase is out of bounds."); 742 743 iterator N = I; 744 // Shift all elts down one. 745 std::move(I+1, this->end(), I); 746 // Drop the last elt. 747 this->pop_back(); 748 return(N); 749 } 750 751 iterator erase(const_iterator CS, const_iterator CE) { 752 // Just cast away constness because this is a non-const member function. 753 iterator S = const_cast<iterator>(CS); 754 iterator E = const_cast<iterator>(CE); 755 756 assert(this->isRangeInStorage(S, E) && "Range to erase is out of bounds."); 757 758 iterator N = S; 759 // Shift all elts down. 760 iterator I = std::move(E, this->end(), S); 761 // Drop the last elts. 762 this->destroy_range(I, this->end()); 763 this->set_size(I - this->begin()); 764 return(N); 765 } 766 767 private: 768 template <class ArgType> iterator insert_one_impl(iterator I, ArgType &&Elt) { 769 // Callers ensure that ArgType is derived from T. 770 static_assert( 771 std::is_same<std::remove_const_t<std::remove_reference_t<ArgType>>, 772 T>::value, 773 "ArgType must be derived from T!"); 774 775 if (I == this->end()) { // Important special case for empty vector. 776 this->push_back(::std::forward<ArgType>(Elt)); 777 return this->end()-1; 778 } 779 780 assert(this->isReferenceToStorage(I) && "Insertion iterator is out of bounds."); 781 782 // Grow if necessary. 783 size_t Index = I - this->begin(); 784 std::remove_reference_t<ArgType> *EltPtr = 785 this->reserveForParamAndGetAddress(Elt); 786 I = this->begin() + Index; 787 788 ::new ((void*) this->end()) T(::std::move(this->back())); 789 // Push everything else over. 790 std::move_backward(I, this->end()-1, this->end()); 791 this->set_size(this->size() + 1); 792 793 // If we just moved the element we're inserting, be sure to update 794 // the reference (never happens if TakesParamByValue). 795 static_assert(!TakesParamByValue || std::is_same<ArgType, T>::value, 796 "ArgType must be 'T' when taking by value!"); 797 if (!TakesParamByValue && this->isReferenceToRange(EltPtr, I, this->end())) 798 ++EltPtr; 799 800 *I = ::std::forward<ArgType>(*EltPtr); 801 return I; 802 } 803 804 public: 805 iterator insert(iterator I, T &&Elt) { 806 return insert_one_impl(I, this->forward_value_param(std::move(Elt))); 807 } 808 809 iterator insert(iterator I, const T &Elt) { 810 return insert_one_impl(I, this->forward_value_param(Elt)); 811 } 812 813 iterator insert(iterator I, size_type NumToInsert, ValueParamT Elt) { 814 // Convert iterator to elt# to avoid invalidating iterator when we reserve() 815 size_t InsertElt = I - this->begin(); 816 817 if (I == this->end()) { // Important special case for empty vector. 818 append(NumToInsert, Elt); 819 return this->begin()+InsertElt; 820 } 821 822 assert(this->isReferenceToStorage(I) && "Insertion iterator is out of bounds."); 823 824 // Ensure there is enough space, and get the (maybe updated) address of 825 // Elt. 826 const T *EltPtr = this->reserveForParamAndGetAddress(Elt, NumToInsert); 827 828 // Uninvalidate the iterator. 829 I = this->begin()+InsertElt; 830 831 // If there are more elements between the insertion point and the end of the 832 // range than there are being inserted, we can use a simple approach to 833 // insertion. Since we already reserved space, we know that this won't 834 // reallocate the vector. 835 if (size_t(this->end()-I) >= NumToInsert) { 836 T *OldEnd = this->end(); 837 append(std::move_iterator<iterator>(this->end() - NumToInsert), 838 std::move_iterator<iterator>(this->end())); 839 840 // Copy the existing elements that get replaced. 841 std::move_backward(I, OldEnd-NumToInsert, OldEnd); 842 843 // If we just moved the element we're inserting, be sure to update 844 // the reference (never happens if TakesParamByValue). 845 if (!TakesParamByValue && I <= EltPtr && EltPtr < this->end()) 846 EltPtr += NumToInsert; 847 848 std::fill_n(I, NumToInsert, *EltPtr); 849 return I; 850 } 851 852 // Otherwise, we're inserting more elements than exist already, and we're 853 // not inserting at the end. 854 855 // Move over the elements that we're about to overwrite. 856 T *OldEnd = this->end(); 857 this->set_size(this->size() + NumToInsert); 858 size_t NumOverwritten = OldEnd-I; 859 this->uninitialized_move(I, OldEnd, this->end()-NumOverwritten); 860 861 // If we just moved the element we're inserting, be sure to update 862 // the reference (never happens if TakesParamByValue). 863 if (!TakesParamByValue && I <= EltPtr && EltPtr < this->end()) 864 EltPtr += NumToInsert; 865 866 // Replace the overwritten part. 867 std::fill_n(I, NumOverwritten, *EltPtr); 868 869 // Insert the non-overwritten middle part. 870 std::uninitialized_fill_n(OldEnd, NumToInsert - NumOverwritten, *EltPtr); 871 return I; 872 } 873 874 template <typename ItTy, typename = EnableIfConvertibleToInputIterator<ItTy>> 875 iterator insert(iterator I, ItTy From, ItTy To) { 876 // Convert iterator to elt# to avoid invalidating iterator when we reserve() 877 size_t InsertElt = I - this->begin(); 878 879 if (I == this->end()) { // Important special case for empty vector. 880 append(From, To); 881 return this->begin()+InsertElt; 882 } 883 884 assert(this->isReferenceToStorage(I) && "Insertion iterator is out of bounds."); 885 886 // Check that the reserve that follows doesn't invalidate the iterators. 887 this->assertSafeToAddRange(From, To); 888 889 size_t NumToInsert = std::distance(From, To); 890 891 // Ensure there is enough space. 892 reserve(this->size() + NumToInsert); 893 894 // Uninvalidate the iterator. 895 I = this->begin()+InsertElt; 896 897 // If there are more elements between the insertion point and the end of the 898 // range than there are being inserted, we can use a simple approach to 899 // insertion. Since we already reserved space, we know that this won't 900 // reallocate the vector. 901 if (size_t(this->end()-I) >= NumToInsert) { 902 T *OldEnd = this->end(); 903 append(std::move_iterator<iterator>(this->end() - NumToInsert), 904 std::move_iterator<iterator>(this->end())); 905 906 // Copy the existing elements that get replaced. 907 std::move_backward(I, OldEnd-NumToInsert, OldEnd); 908 909 std::copy(From, To, I); 910 return I; 911 } 912 913 // Otherwise, we're inserting more elements than exist already, and we're 914 // not inserting at the end. 915 916 // Move over the elements that we're about to overwrite. 917 T *OldEnd = this->end(); 918 this->set_size(this->size() + NumToInsert); 919 size_t NumOverwritten = OldEnd-I; 920 this->uninitialized_move(I, OldEnd, this->end()-NumOverwritten); 921 922 // Replace the overwritten part. 923 for (T *J = I; NumOverwritten > 0; --NumOverwritten) { 924 *J = *From; 925 ++J; ++From; 926 } 927 928 // Insert the non-overwritten middle part. 929 this->uninitialized_copy(From, To, OldEnd); 930 return I; 931 } 932 933 void insert(iterator I, std::initializer_list<T> IL) { 934 insert(I, IL.begin(), IL.end()); 935 } 936 937 template <typename... ArgTypes> reference emplace_back(ArgTypes &&... Args) { 938 if (LLVM_UNLIKELY(this->size() >= this->capacity())) 939 return this->growAndEmplaceBack(std::forward<ArgTypes>(Args)...); 940 941 ::new ((void *)this->end()) T(std::forward<ArgTypes>(Args)...); 942 this->set_size(this->size() + 1); 943 return this->back(); 944 } 945 946 SmallVectorImpl &operator=(const SmallVectorImpl &RHS); 947 948 SmallVectorImpl &operator=(SmallVectorImpl &&RHS); 949 950 bool operator==(const SmallVectorImpl &RHS) const { 951 if (this->size() != RHS.size()) return false; 952 return std::equal(this->begin(), this->end(), RHS.begin()); 953 } 954 bool operator!=(const SmallVectorImpl &RHS) const { 955 return !(*this == RHS); 956 } 957 958 bool operator<(const SmallVectorImpl &RHS) const { 959 return std::lexicographical_compare(this->begin(), this->end(), 960 RHS.begin(), RHS.end()); 961 } 962 bool operator>(const SmallVectorImpl &RHS) const { return RHS < *this; } 963 bool operator<=(const SmallVectorImpl &RHS) const { return !(*this > RHS); } 964 bool operator>=(const SmallVectorImpl &RHS) const { return !(*this < RHS); } 965 }; 966 967 template <typename T> 968 void SmallVectorImpl<T>::swap(SmallVectorImpl<T> &RHS) { 969 if (this == &RHS) return; 970 971 // We can only avoid copying elements if neither vector is small. 972 if (!this->isSmall() && !RHS.isSmall()) { 973 std::swap(this->BeginX, RHS.BeginX); 974 std::swap(this->Size, RHS.Size); 975 std::swap(this->Capacity, RHS.Capacity); 976 return; 977 } 978 this->reserve(RHS.size()); 979 RHS.reserve(this->size()); 980 981 // Swap the shared elements. 982 size_t NumShared = this->size(); 983 if (NumShared > RHS.size()) NumShared = RHS.size(); 984 for (size_type i = 0; i != NumShared; ++i) 985 std::swap((*this)[i], RHS[i]); 986 987 // Copy over the extra elts. 988 if (this->size() > RHS.size()) { 989 size_t EltDiff = this->size() - RHS.size(); 990 this->uninitialized_copy(this->begin()+NumShared, this->end(), RHS.end()); 991 RHS.set_size(RHS.size() + EltDiff); 992 this->destroy_range(this->begin()+NumShared, this->end()); 993 this->set_size(NumShared); 994 } else if (RHS.size() > this->size()) { 995 size_t EltDiff = RHS.size() - this->size(); 996 this->uninitialized_copy(RHS.begin()+NumShared, RHS.end(), this->end()); 997 this->set_size(this->size() + EltDiff); 998 this->destroy_range(RHS.begin()+NumShared, RHS.end()); 999 RHS.set_size(NumShared); 1000 } 1001 } 1002 1003 template <typename T> 1004 SmallVectorImpl<T> &SmallVectorImpl<T>:: 1005 operator=(const SmallVectorImpl<T> &RHS) { 1006 // Avoid self-assignment. 1007 if (this == &RHS) return *this; 1008 1009 // If we already have sufficient space, assign the common elements, then 1010 // destroy any excess. 1011 size_t RHSSize = RHS.size(); 1012 size_t CurSize = this->size(); 1013 if (CurSize >= RHSSize) { 1014 // Assign common elements. 1015 iterator NewEnd; 1016 if (RHSSize) 1017 NewEnd = std::copy(RHS.begin(), RHS.begin()+RHSSize, this->begin()); 1018 else 1019 NewEnd = this->begin(); 1020 1021 // Destroy excess elements. 1022 this->destroy_range(NewEnd, this->end()); 1023 1024 // Trim. 1025 this->set_size(RHSSize); 1026 return *this; 1027 } 1028 1029 // If we have to grow to have enough elements, destroy the current elements. 1030 // This allows us to avoid copying them during the grow. 1031 // FIXME: don't do this if they're efficiently moveable. 1032 if (this->capacity() < RHSSize) { 1033 // Destroy current elements. 1034 this->clear(); 1035 CurSize = 0; 1036 this->grow(RHSSize); 1037 } else if (CurSize) { 1038 // Otherwise, use assignment for the already-constructed elements. 1039 std::copy(RHS.begin(), RHS.begin()+CurSize, this->begin()); 1040 } 1041 1042 // Copy construct the new elements in place. 1043 this->uninitialized_copy(RHS.begin()+CurSize, RHS.end(), 1044 this->begin()+CurSize); 1045 1046 // Set end. 1047 this->set_size(RHSSize); 1048 return *this; 1049 } 1050 1051 template <typename T> 1052 SmallVectorImpl<T> &SmallVectorImpl<T>::operator=(SmallVectorImpl<T> &&RHS) { 1053 // Avoid self-assignment. 1054 if (this == &RHS) return *this; 1055 1056 // If the RHS isn't small, clear this vector and then steal its buffer. 1057 if (!RHS.isSmall()) { 1058 this->assignRemote(std::move(RHS)); 1059 return *this; 1060 } 1061 1062 // If we already have sufficient space, assign the common elements, then 1063 // destroy any excess. 1064 size_t RHSSize = RHS.size(); 1065 size_t CurSize = this->size(); 1066 if (CurSize >= RHSSize) { 1067 // Assign common elements. 1068 iterator NewEnd = this->begin(); 1069 if (RHSSize) 1070 NewEnd = std::move(RHS.begin(), RHS.end(), NewEnd); 1071 1072 // Destroy excess elements and trim the bounds. 1073 this->destroy_range(NewEnd, this->end()); 1074 this->set_size(RHSSize); 1075 1076 // Clear the RHS. 1077 RHS.clear(); 1078 1079 return *this; 1080 } 1081 1082 // If we have to grow to have enough elements, destroy the current elements. 1083 // This allows us to avoid copying them during the grow. 1084 // FIXME: this may not actually make any sense if we can efficiently move 1085 // elements. 1086 if (this->capacity() < RHSSize) { 1087 // Destroy current elements. 1088 this->clear(); 1089 CurSize = 0; 1090 this->grow(RHSSize); 1091 } else if (CurSize) { 1092 // Otherwise, use assignment for the already-constructed elements. 1093 std::move(RHS.begin(), RHS.begin()+CurSize, this->begin()); 1094 } 1095 1096 // Move-construct the new elements in place. 1097 this->uninitialized_move(RHS.begin()+CurSize, RHS.end(), 1098 this->begin()+CurSize); 1099 1100 // Set end. 1101 this->set_size(RHSSize); 1102 1103 RHS.clear(); 1104 return *this; 1105 } 1106 1107 /// Storage for the SmallVector elements. This is specialized for the N=0 case 1108 /// to avoid allocating unnecessary storage. 1109 template <typename T, unsigned N> 1110 struct SmallVectorStorage { 1111 alignas(T) char InlineElts[N * sizeof(T)]; 1112 }; 1113 1114 /// We need the storage to be properly aligned even for small-size of 0 so that 1115 /// the pointer math in \a SmallVectorTemplateCommon::getFirstEl() is 1116 /// well-defined. 1117 template <typename T> struct alignas(T) SmallVectorStorage<T, 0> {}; 1118 1119 /// Forward declaration of SmallVector so that 1120 /// calculateSmallVectorDefaultInlinedElements can reference 1121 /// `sizeof(SmallVector<T, 0>)`. 1122 template <typename T, unsigned N> class LLVM_GSL_OWNER SmallVector; 1123 1124 /// Helper class for calculating the default number of inline elements for 1125 /// `SmallVector<T>`. 1126 /// 1127 /// This should be migrated to a constexpr function when our minimum 1128 /// compiler support is enough for multi-statement constexpr functions. 1129 template <typename T> struct CalculateSmallVectorDefaultInlinedElements { 1130 // Parameter controlling the default number of inlined elements 1131 // for `SmallVector<T>`. 1132 // 1133 // The default number of inlined elements ensures that 1134 // 1. There is at least one inlined element. 1135 // 2. `sizeof(SmallVector<T>) <= kPreferredSmallVectorSizeof` unless 1136 // it contradicts 1. 1137 static constexpr size_t kPreferredSmallVectorSizeof = 64; 1138 1139 // static_assert that sizeof(T) is not "too big". 1140 // 1141 // Because our policy guarantees at least one inlined element, it is possible 1142 // for an arbitrarily large inlined element to allocate an arbitrarily large 1143 // amount of inline storage. We generally consider it an antipattern for a 1144 // SmallVector to allocate an excessive amount of inline storage, so we want 1145 // to call attention to these cases and make sure that users are making an 1146 // intentional decision if they request a lot of inline storage. 1147 // 1148 // We want this assertion to trigger in pathological cases, but otherwise 1149 // not be too easy to hit. To accomplish that, the cutoff is actually somewhat 1150 // larger than kPreferredSmallVectorSizeof (otherwise, 1151 // `SmallVector<SmallVector<T>>` would be one easy way to trip it, and that 1152 // pattern seems useful in practice). 1153 // 1154 // One wrinkle is that this assertion is in theory non-portable, since 1155 // sizeof(T) is in general platform-dependent. However, we don't expect this 1156 // to be much of an issue, because most LLVM development happens on 64-bit 1157 // hosts, and therefore sizeof(T) is expected to *decrease* when compiled for 1158 // 32-bit hosts, dodging the issue. The reverse situation, where development 1159 // happens on a 32-bit host and then fails due to sizeof(T) *increasing* on a 1160 // 64-bit host, is expected to be very rare. 1161 static_assert( 1162 sizeof(T) <= 256, 1163 "You are trying to use a default number of inlined elements for " 1164 "`SmallVector<T>` but `sizeof(T)` is really big! Please use an " 1165 "explicit number of inlined elements with `SmallVector<T, N>` to make " 1166 "sure you really want that much inline storage."); 1167 1168 // Discount the size of the header itself when calculating the maximum inline 1169 // bytes. 1170 static constexpr size_t PreferredInlineBytes = 1171 kPreferredSmallVectorSizeof - sizeof(SmallVector<T, 0>); 1172 static constexpr size_t NumElementsThatFit = PreferredInlineBytes / sizeof(T); 1173 static constexpr size_t value = 1174 NumElementsThatFit == 0 ? 1 : NumElementsThatFit; 1175 }; 1176 1177 /// This is a 'vector' (really, a variable-sized array), optimized 1178 /// for the case when the array is small. It contains some number of elements 1179 /// in-place, which allows it to avoid heap allocation when the actual number of 1180 /// elements is below that threshold. This allows normal "small" cases to be 1181 /// fast without losing generality for large inputs. 1182 /// 1183 /// \note 1184 /// In the absence of a well-motivated choice for the number of inlined 1185 /// elements \p N, it is recommended to use \c SmallVector<T> (that is, 1186 /// omitting the \p N). This will choose a default number of inlined elements 1187 /// reasonable for allocation on the stack (for example, trying to keep \c 1188 /// sizeof(SmallVector<T>) around 64 bytes). 1189 /// 1190 /// \warning This does not attempt to be exception safe. 1191 /// 1192 /// \see https://llvm.org/docs/ProgrammersManual.html#llvm-adt-smallvector-h 1193 template <typename T, 1194 unsigned N = CalculateSmallVectorDefaultInlinedElements<T>::value> 1195 class LLVM_GSL_OWNER SmallVector : public SmallVectorImpl<T>, 1196 SmallVectorStorage<T, N> { 1197 public: 1198 SmallVector() : SmallVectorImpl<T>(N) {} 1199 1200 ~SmallVector() { 1201 // Destroy the constructed elements in the vector. 1202 this->destroy_range(this->begin(), this->end()); 1203 } 1204 1205 explicit SmallVector(size_t Size) 1206 : SmallVectorImpl<T>(N) { 1207 this->resize(Size); 1208 } 1209 1210 SmallVector(size_t Size, const T &Value) 1211 : SmallVectorImpl<T>(N) { 1212 this->assign(Size, Value); 1213 } 1214 1215 template <typename ItTy, typename = EnableIfConvertibleToInputIterator<ItTy>> 1216 SmallVector(ItTy S, ItTy E) : SmallVectorImpl<T>(N) { 1217 this->append(S, E); 1218 } 1219 1220 template <typename RangeTy> 1221 explicit SmallVector(const iterator_range<RangeTy> &R) 1222 : SmallVectorImpl<T>(N) { 1223 this->append(R.begin(), R.end()); 1224 } 1225 1226 SmallVector(std::initializer_list<T> IL) : SmallVectorImpl<T>(N) { 1227 this->append(IL); 1228 } 1229 1230 template <typename U, 1231 typename = std::enable_if_t<std::is_convertible<U, T>::value>> 1232 explicit SmallVector(ArrayRef<U> A) : SmallVectorImpl<T>(N) { 1233 this->append(A.begin(), A.end()); 1234 } 1235 1236 SmallVector(const SmallVector &RHS) : SmallVectorImpl<T>(N) { 1237 if (!RHS.empty()) 1238 SmallVectorImpl<T>::operator=(RHS); 1239 } 1240 1241 SmallVector &operator=(const SmallVector &RHS) { 1242 SmallVectorImpl<T>::operator=(RHS); 1243 return *this; 1244 } 1245 1246 SmallVector(SmallVector &&RHS) : SmallVectorImpl<T>(N) { 1247 if (!RHS.empty()) 1248 SmallVectorImpl<T>::operator=(::std::move(RHS)); 1249 } 1250 1251 SmallVector(SmallVectorImpl<T> &&RHS) : SmallVectorImpl<T>(N) { 1252 if (!RHS.empty()) 1253 SmallVectorImpl<T>::operator=(::std::move(RHS)); 1254 } 1255 1256 SmallVector &operator=(SmallVector &&RHS) { 1257 if (N) { 1258 SmallVectorImpl<T>::operator=(::std::move(RHS)); 1259 return *this; 1260 } 1261 // SmallVectorImpl<T>::operator= does not leverage N==0. Optimize the 1262 // case. 1263 if (this == &RHS) 1264 return *this; 1265 if (RHS.empty()) { 1266 this->destroy_range(this->begin(), this->end()); 1267 this->Size = 0; 1268 } else { 1269 this->assignRemote(std::move(RHS)); 1270 } 1271 return *this; 1272 } 1273 1274 SmallVector &operator=(SmallVectorImpl<T> &&RHS) { 1275 SmallVectorImpl<T>::operator=(::std::move(RHS)); 1276 return *this; 1277 } 1278 1279 SmallVector &operator=(std::initializer_list<T> IL) { 1280 this->assign(IL); 1281 return *this; 1282 } 1283 }; 1284 1285 template <typename T, unsigned N> 1286 inline size_t capacity_in_bytes(const SmallVector<T, N> &X) { 1287 return X.capacity_in_bytes(); 1288 } 1289 1290 template <typename RangeType> 1291 using ValueTypeFromRangeType = 1292 std::remove_const_t<std::remove_reference_t<decltype(*std::begin( 1293 std::declval<RangeType &>()))>>; 1294 1295 /// Given a range of type R, iterate the entire range and return a 1296 /// SmallVector with elements of the vector. This is useful, for example, 1297 /// when you want to iterate a range and then sort the results. 1298 template <unsigned Size, typename R> 1299 SmallVector<ValueTypeFromRangeType<R>, Size> to_vector(R &&Range) { 1300 return {std::begin(Range), std::end(Range)}; 1301 } 1302 template <typename R> 1303 SmallVector<ValueTypeFromRangeType<R>> to_vector(R &&Range) { 1304 return {std::begin(Range), std::end(Range)}; 1305 } 1306 1307 template <typename Out, unsigned Size, typename R> 1308 SmallVector<Out, Size> to_vector_of(R &&Range) { 1309 return {std::begin(Range), std::end(Range)}; 1310 } 1311 1312 template <typename Out, typename R> SmallVector<Out> to_vector_of(R &&Range) { 1313 return {std::begin(Range), std::end(Range)}; 1314 } 1315 1316 // Explicit instantiations 1317 extern template class llvm::SmallVectorBase<uint32_t>; 1318 #if SIZE_MAX > UINT32_MAX 1319 extern template class llvm::SmallVectorBase<uint64_t>; 1320 #endif 1321 1322 } // end namespace llvm 1323 1324 namespace std { 1325 1326 /// Implement std::swap in terms of SmallVector swap. 1327 template<typename T> 1328 inline void 1329 swap(llvm::SmallVectorImpl<T> &LHS, llvm::SmallVectorImpl<T> &RHS) { 1330 LHS.swap(RHS); 1331 } 1332 1333 /// Implement std::swap in terms of SmallVector swap. 1334 template<typename T, unsigned N> 1335 inline void 1336 swap(llvm::SmallVector<T, N> &LHS, llvm::SmallVector<T, N> &RHS) { 1337 LHS.swap(RHS); 1338 } 1339 1340 } // end namespace std 1341 1342 #endif // LLVM_ADT_SMALLVECTOR_H 1343