AWS SDK for C++  0.14.3
AWS SDK for C++
AWSMemory.h
Go to the documentation of this file.
1 /*
2  * Copyright 2010-2016 Amazon.com, Inc. or its affiliates. All Rights Reserved.
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License").
5  * You may not use this file except in compliance with the License.
6  * A copy of the License is located at
7  *
8  * http://aws.amazon.com/apache2.0
9  *
10  * or in the "license" file accompanying this file. This file is distributed
11  * on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either
12  * express or implied. See the License for the specific language governing
13  * permissions and limitations under the License.
14  */
15 
16 #pragma once
17 
18 #include <aws/core/Core_EXPORTS.h>
21 
22 #include <memory>
23 #include <cstdlib>
24 
25 namespace Aws
26 {
27  namespace Utils
28  {
29  namespace Memory
30  {
35 
40 
45 
46  } // namespace Memory
47  } // namespace Utils
48 
53  AWS_CORE_API void* Malloc(const char* allocationTag, size_t allocationSize);
54 
59  AWS_CORE_API void Free(void* memoryPtr);
60 
65  template<typename T, typename ...ArgTypes>
66  T* New(const char* allocationTag, ArgTypes&&... args)
67  {
68  void *rawMemory = Malloc(allocationTag, sizeof(T));
69 
70  T *constructedMemory = new (rawMemory) T(std::forward<ArgTypes>(args)...);
71  return constructedMemory;
72  }
73 
78  template<typename T>
79  void Delete(T* pointerToT)
80  {
81  if (pointerToT == nullptr)
82  {
83  return;
84  }
85 
86  pointerToT->~T();
87  Free(pointerToT);
88  }
89 
90  template<typename T>
92  {
93  return std::is_class<T>::value;
94  }
95 
96  template<typename T>
98  {
99  return !std::is_trivially_destructible<T>::value;
100  }
101 
106  template<typename T>
107  T* NewArray(std::size_t amount, const char* allocationTag)
108  {
109  if (amount > 0)
110  {
111  bool constructMembers = ShouldConstructArrayMembers<T>();
112  bool trackMemberCount = ShouldDestroyArrayMembers<T>();
113 
114  // if we need to remember the # of items in the array (because we need to call their destructors) then allocate extra memory and keep the # of items in the extra slot
115  std::size_t allocationSize = amount * sizeof(T);
116  if (trackMemberCount)
117  {
118  allocationSize += sizeof(std::size_t);
119  }
120 
121  void* rawMemory = Malloc(allocationTag, allocationSize);
122  T* pointerToT = nullptr;
123 
124  if (trackMemberCount)
125  {
126  std::size_t* pointerToAmount = reinterpret_cast<std::size_t*>(rawMemory);
127  *pointerToAmount = amount;
128  pointerToT = reinterpret_cast<T*>(reinterpret_cast<void*>(pointerToAmount + 1));
129  }
130  else
131  {
132  pointerToT = reinterpret_cast<T*>(rawMemory);
133  }
134 
135  if (constructMembers)
136  {
137  for (std::size_t i = 0; i < amount; ++i)
138  {
139  new (pointerToT + i) T;
140  }
141  }
142 
143  return pointerToT;
144  }
145 
146  return nullptr;
147  }
148 
153  template<typename T>
154  void DeleteArray(T* pointerToTArray)
155  {
156  if (pointerToTArray == nullptr)
157  {
158  return;
159  }
160 
161  bool destroyMembers = ShouldDestroyArrayMembers<T>();
162  void* rawMemory = nullptr;
163 
164  if (destroyMembers)
165  {
166  std::size_t *pointerToAmount = reinterpret_cast<std::size_t *>(reinterpret_cast<void *>(pointerToTArray)) - 1;
167  std::size_t amount = *pointerToAmount;
168 
169  for (std::size_t i = amount; i > 0; --i)
170  {
171  (pointerToTArray + i - 1)->~T();
172  }
173  rawMemory = reinterpret_cast<void *>(pointerToAmount);
174  }
175  else
176  {
177  rawMemory = reinterpret_cast<void *>(pointerToTArray);
178  }
179 
180  Free(rawMemory);
181  }
182 
186  template<typename T>
187  struct Deleter
188  {
189  Deleter() {}
190 
191  template<class U, class = typename std::enable_if<std::is_convertible<U *, T *>::value, void>::type>
193  {
194  }
195 
196  void operator()(T *pointerToT) const
197  {
198  static_assert(0 < sizeof(T), "can't delete an incomplete type");
199  Aws::Delete(pointerToT);
200  }
201  };
202 
203  template< typename T > using UniquePtr = std::unique_ptr< T, Deleter< T > >;
204 
209  template<typename T, typename ...ArgTypes>
210  UniquePtr<T> MakeUnique(const char* allocationTag, ArgTypes&&... args)
211  {
212  return UniquePtr<T>(Aws::New<T>(allocationTag, std::forward<ArgTypes>(args)...));
213  }
214 
215  template<typename T>
217  {
219 
220  template<class U, class = typename std::enable_if<std::is_convertible<U *, T *>::value, void>::type>
222  {
223  }
224 
225  void operator()(T *pointerToTArray) const
226  {
227  static_assert(0 < sizeof(T), "can't delete an incomplete type");
228  Aws::DeleteArray(pointerToTArray);
229  }
230  };
231 
232  template< typename T > using UniqueArrayPtr = std::unique_ptr< T, ArrayDeleter< T > >;
233 
238  template<typename T, typename ...ArgTypes>
239  UniqueArrayPtr<T> MakeUniqueArray(std::size_t amount, const char* allocationTag, ArgTypes&&... args)
240  {
241  return UniqueArrayPtr<T>(Aws::NewArray<T>(amount, allocationTag, std::forward<ArgTypes>(args)...));
242  }
243 
244 
245 } // namespace Aws
246 
void DeleteArray(T *pointerToTArray)
Definition: AWSMemory.h:154
bool ShouldConstructArrayMembers()
Definition: AWSMemory.h:91
void Delete(T *pointerToT)
Definition: AWSMemory.h:79
bool ShouldDestroyArrayMembers()
Definition: AWSMemory.h:97
UniqueArrayPtr< T > MakeUniqueArray(std::size_t amount, const char *allocationTag, ArgTypes &&...args)
Definition: AWSMemory.h:239
void operator()(T *pointerToT) const
Definition: AWSMemory.h:196
ArrayDeleter(const ArrayDeleter< U > &)
Definition: AWSMemory.h:221
AWS_CORE_API void ShutdownAWSMemorySystem(void)
UniquePtr< T > MakeUnique(const char *allocationTag, ArgTypes &&...args)
Definition: AWSMemory.h:210
std::unique_ptr< T, ArrayDeleter< T > > UniqueArrayPtr
Definition: AWSMemory.h:232
AWS_CORE_API void InitializeAWSMemorySystem(MemorySystemInterface &memorySystem)
AWS_CORE_API MemorySystemInterface * GetMemorySystem()
void operator()(T *pointerToTArray) const
Definition: AWSMemory.h:225
AWS_CORE_API void Free(void *memoryPtr)
T * New(const char *allocationTag, ArgTypes &&...args)
Definition: AWSMemory.h:66
std::unique_ptr< T, Deleter< T > > UniquePtr
Definition: AWSMemory.h:203
T * NewArray(std::size_t amount, const char *allocationTag)
Definition: AWSMemory.h:107
AWS_CORE_API void * Malloc(const char *allocationTag, size_t allocationSize)
#define AWS_CORE_API
Definition: Core_EXPORTS.h:35
JSON (JavaScript Object Notation).
Deleter(const Deleter< U > &)
Definition: AWSMemory.h:192