about summary refs log tree commit diff
path: root/absl/container/internal
diff options
context:
space:
mode:
authorAbseil Team <absl-team@google.com>2019-06-05T15·26-0700
committerXiaoyi Zhang <zhangxy988@gmail.com>2019-06-05T16·00-0400
commit61c9bf3e3e1c28a4aa6d7f1be4b37fd473bb5529 (patch)
tree864940b164bac77a57acf02614f812c44484d7d2 /absl/container/internal
parentbc9101f9982391019521161a36179b52555ed212 (diff)
Export of internal Abseil changes.
--
39b55fafbe4a83f9f0524544a12d4ed02fdec751 by Xiaoyi Zhang <zhangxy@google.com>:

Avoid -Wundef warning of macro `ABSL_HAVE_ELF_MEM_IMAGE`.
This is github pull request https://github.com/abseil/abseil-cpp/pull/320.

PiperOrigin-RevId: 251646785

--
2fbf0de42d6723088211cb23444f16ecadcc7d67 by Abseil Team <absl-team@google.com>:

Add missing dependency on base:dynamic_annotations.

The target absl/debugging:symbolize includes dynamic_annotations from absl/debugging/symbolize_elf.inc.

PiperOrigin-RevId: 251430877

--
2537de6f01458938684f4818606ba5ce3f1c3cdf by CJ Johnson <johnsoncj@google.com>:

In InlinedVector: Combines storage_.SetAllocatedData(...) and storage_.SetAllocatedCapacity(...) into a single two-arg function also called storage_.SetAllocatedData(...) such that data and capacity must always be set together

PiperOrigin-RevId: 251331883

--
c05252c01710ac28d2c3defd09acfc55ecf2b8f1 by CJ Johnson <johnsoncj@google.com>:

So that InlinedVector constructors do no leak allocations when throwing exceptions, this CL moves the call to `clear()` from `~InlinedVector()` to `~Storage()`

In addition, noexcept specifiers have been added where appropriate (Copy construction and default construction on std::allocator are noexcept. See CppRef: https://en.cppreference.com/w/cpp/memory/allocator/allocator)

PiperOrigin-RevId: 251256272

--
34ce8367a8e29a0dea950c0e2967dd7cfdbd5d33 by CJ Johnson <johnsoncj@google.com>:

Cleans up InlinedVector constructors by inlining Impl functions with only one caller and dispatching where appropriate

PiperOrigin-RevId: 250919357
GitOrigin-RevId: 39b55fafbe4a83f9f0524544a12d4ed02fdec751
Change-Id: I21e8866582e6e02afb2c54f7347d624053e9ce45
Diffstat (limited to 'absl/container/internal')
-rw-r--r--absl/container/internal/inlined_vector.h44
1 files changed, 41 insertions, 3 deletions
diff --git a/absl/container/internal/inlined_vector.h b/absl/container/internal/inlined_vector.h
index 79533a41f3d2..f4eb92ec169a 100644
--- a/absl/container/internal/inlined_vector.h
+++ b/absl/container/internal/inlined_vector.h
@@ -52,6 +52,16 @@ void DestroyElements(AllocatorType* alloc_ptr, ValueType* destroy_first,
 #endif  // NDEBUG
 }
 
+template <typename AllocatorType>
+struct StorageView {
+  using pointer = typename AllocatorType::pointer;
+  using size_type = typename AllocatorType::size_type;
+
+  pointer data;
+  size_type size;
+  size_type capacity;
+};
+
 template <typename T, size_t N, typename A>
 class Storage {
  public:
@@ -70,9 +80,15 @@ class Storage {
   using const_reverse_iterator = std::reverse_iterator<const_iterator>;
   using AllocatorTraits = absl::allocator_traits<allocator_type>;
 
+  using StorageView = inlined_vector_internal::StorageView<allocator_type>;
+
+  Storage() : metadata_() {}
+
   explicit Storage(const allocator_type& alloc)
       : metadata_(alloc, /* empty and inlined */ 0) {}
 
+  ~Storage() { DestroyAndDeallocate(); }
+
   size_type GetSize() const { return GetSizeAndIsAllocated() >> 1; }
 
   bool GetIsAllocated() const { return GetSizeAndIsAllocated() & 1; }
@@ -97,6 +113,13 @@ class Storage {
     return data_.allocated.allocated_capacity;
   }
 
+  StorageView MakeStorageView() {
+    return GetIsAllocated() ? StorageView{GetAllocatedData(), GetSize(),
+                                          GetAllocatedCapacity()}
+                            : StorageView{GetInlinedData(), GetSize(),
+                                          static_cast<size_type>(N)};
+  }
+
   allocator_type* GetAllocPtr() {
     return std::addressof(metadata_.template get<0>());
   }
@@ -113,9 +136,8 @@ class Storage {
 
   void AddSize(size_type count) { GetSizeAndIsAllocated() += count << 1; }
 
-  void SetAllocatedData(pointer data) { data_.allocated.allocated_data = data; }
-
-  void SetAllocatedCapacity(size_type capacity) {
+  void SetAllocatedData(pointer data, size_type capacity) {
+    data_.allocated.allocated_data = data;
     data_.allocated.allocated_capacity = capacity;
   }
 
@@ -129,6 +151,8 @@ class Storage {
     swap(data_.allocated, other->data_.allocated);
   }
 
+  void DestroyAndDeallocate();
+
  private:
   size_type& GetSizeAndIsAllocated() { return metadata_.template get<1>(); }
 
@@ -159,6 +183,20 @@ class Storage {
   Data data_;
 };
 
+template <typename T, size_t N, typename A>
+void Storage<T, N, A>::DestroyAndDeallocate() {
+  namespace ivi = inlined_vector_internal;
+
+  StorageView storage_view = MakeStorageView();
+
+  ivi::DestroyElements(GetAllocPtr(), storage_view.data, storage_view.size);
+
+  if (GetIsAllocated()) {
+    AllocatorTraits::deallocate(*GetAllocPtr(), storage_view.data,
+                                storage_view.capacity);
+  }
+}
+
 }  // namespace inlined_vector_internal
 }  // namespace absl