sanitizer_vector.h revision 341825
1//===-- sanitizer_vector.h -------------------------------------*- C++ -*-===// 2// 3// The LLVM Compiler Infrastructure 4// 5// This file is distributed under the University of Illinois Open Source 6// License. See LICENSE.TXT for details. 7// 8//===----------------------------------------------------------------------===// 9// 10// This file is shared between sanitizers run-time libraries. 11// 12//===----------------------------------------------------------------------===// 13 14// Low-fat STL-like vector container. 15 16#ifndef SANITIZER_VECTOR_H 17#define SANITIZER_VECTOR_H 18 19#include "sanitizer_common/sanitizer_allocator_internal.h" 20#include "sanitizer_common/sanitizer_libc.h" 21 22namespace __sanitizer { 23 24template<typename T> 25class Vector { 26 public: 27 explicit Vector() 28 : begin_() 29 , end_() 30 , last_() { 31 } 32 33 ~Vector() { 34 if (begin_) 35 InternalFree(begin_); 36 } 37 38 void Reset() { 39 if (begin_) 40 InternalFree(begin_); 41 begin_ = 0; 42 end_ = 0; 43 last_ = 0; 44 } 45 46 uptr Size() const { 47 return end_ - begin_; 48 } 49 50 T &operator[](uptr i) { 51 DCHECK_LT(i, end_ - begin_); 52 return begin_[i]; 53 } 54 55 const T &operator[](uptr i) const { 56 DCHECK_LT(i, end_ - begin_); 57 return begin_[i]; 58 } 59 60 T *PushBack() { 61 EnsureSize(Size() + 1); 62 T *p = &end_[-1]; 63 internal_memset(p, 0, sizeof(*p)); 64 return p; 65 } 66 67 T *PushBack(const T& v) { 68 EnsureSize(Size() + 1); 69 T *p = &end_[-1]; 70 internal_memcpy(p, &v, sizeof(*p)); 71 return p; 72 } 73 74 void PopBack() { 75 DCHECK_GT(end_, begin_); 76 end_--; 77 } 78 79 void Resize(uptr size) { 80 if (size == 0) { 81 end_ = begin_; 82 return; 83 } 84 uptr old_size = Size(); 85 if (size <= old_size) { 86 end_ = begin_ + size; 87 return; 88 } 89 EnsureSize(size); 90 if (old_size < size) { 91 for (uptr i = old_size; i < size; i++) 92 internal_memset(&begin_[i], 0, sizeof(begin_[i])); 93 } 94 } 95 96 private: 97 T *begin_; 98 T *end_; 99 T *last_; 100 101 void EnsureSize(uptr size) { 102 if (size <= Size()) 103 return; 104 if (size <= (uptr)(last_ - begin_)) { 105 end_ = begin_ + size; 106 return; 107 } 108 uptr cap0 = last_ - begin_; 109 uptr cap = cap0 * 5 / 4; // 25% growth 110 if (cap == 0) 111 cap = 16; 112 if (cap < size) 113 cap = size; 114 T *p = (T*)InternalAlloc(cap * sizeof(T)); 115 if (cap0) { 116 internal_memcpy(p, begin_, cap0 * sizeof(T)); 117 InternalFree(begin_); 118 } 119 begin_ = p; 120 end_ = begin_ + size; 121 last_ = begin_ + cap; 122 } 123 124 Vector(const Vector&); 125 void operator=(const Vector&); 126}; 127} // namespace __sanitizer 128 129#endif // #ifndef SANITIZER_VECTOR_H 130