memory 12 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383
  1. // <memory> -*- C++ -*-
  2. // Copyright (C) 2001-2019 Free Software Foundation, Inc.
  3. //
  4. // This file is part of the GNU ISO C++ Library. This library is free
  5. // software; you can redistribute it and/or modify it under the
  6. // terms of the GNU General Public License as published by the
  7. // Free Software Foundation; either version 3, or (at your option)
  8. // any later version.
  9. // This library is distributed in the hope that it will be useful,
  10. // but WITHOUT ANY WARRANTY; without even the implied warranty of
  11. // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  12. // GNU General Public License for more details.
  13. // Under Section 7 of GPL version 3, you are granted additional
  14. // permissions described in the GCC Runtime Library Exception, version
  15. // 3.1, as published by the Free Software Foundation.
  16. // You should have received a copy of the GNU General Public License and
  17. // a copy of the GCC Runtime Library Exception along with this program;
  18. // see the files COPYING3 and COPYING.RUNTIME respectively. If not, see
  19. // <http://www.gnu.org/licenses/>.
  20. /*
  21. * Copyright (c) 1997-1999
  22. * Silicon Graphics Computer Systems, Inc.
  23. *
  24. * Permission to use, copy, modify, distribute and sell this software
  25. * and its documentation for any purpose is hereby granted without fee,
  26. * provided that the above copyright notice appear in all copies and
  27. * that both that copyright notice and this permission notice appear
  28. * in supporting documentation. Silicon Graphics makes no
  29. * representations about the suitability of this software for any
  30. * purpose. It is provided "as is" without express or implied warranty.
  31. *
  32. */
  33. /** @file include/memory
  34. * This is a Standard C++ Library header.
  35. */
  36. #ifndef _GLIBCXX_MEMORY
  37. #define _GLIBCXX_MEMORY 1
  38. #pragma GCC system_header
  39. /**
  40. * @defgroup memory Memory
  41. * @ingroup utilities
  42. *
  43. * Components for memory allocation, deallocation, and management.
  44. */
  45. /**
  46. * @defgroup pointer_abstractions Pointer Abstractions
  47. * @ingroup memory
  48. *
  49. * Smart pointers, etc.
  50. */
  51. #include <bits/stl_algobase.h>
  52. #include <bits/allocator.h>
  53. #include <bits/stl_construct.h>
  54. #include <bits/stl_uninitialized.h>
  55. #include <bits/stl_tempbuf.h>
  56. #include <bits/stl_raw_storage_iter.h>
  57. #if __cplusplus >= 201103L
  58. # include <exception> // std::exception
  59. # include <typeinfo> // std::type_info in get_deleter
  60. # include <iosfwd> // std::basic_ostream
  61. # include <ext/atomicity.h>
  62. # include <ext/concurrence.h>
  63. # include <bits/functexcept.h>
  64. # include <bits/stl_function.h> // std::less
  65. # include <bits/uses_allocator.h>
  66. # include <type_traits>
  67. # include <debug/debug.h>
  68. # include <bits/unique_ptr.h>
  69. # include <bits/shared_ptr.h>
  70. # include <bits/shared_ptr_atomic.h>
  71. # if _GLIBCXX_USE_DEPRECATED
  72. # include <backward/auto_ptr.h>
  73. # endif
  74. #else
  75. # include <backward/auto_ptr.h>
  76. #endif
  77. #if __cplusplus >= 201103L
  78. #include <cstdint>
  79. #if __cplusplus > 201703L
  80. # include <bit> // for ispow2
  81. # include <new> // for placement operator new
  82. # include <tuple> // for tuple, make_tuple, make_from_tuple
  83. #endif
  84. namespace std _GLIBCXX_VISIBILITY(default)
  85. {
  86. _GLIBCXX_BEGIN_NAMESPACE_VERSION
  87. /**
  88. * @brief Fit aligned storage in buffer.
  89. *
  90. * [ptr.align]
  91. *
  92. * This function tries to fit @a __size bytes of storage with alignment
  93. * @a __align into the buffer @a __ptr of size @a __space bytes. If such
  94. * a buffer fits then @a __ptr is changed to point to the first byte of the
  95. * aligned storage and @a __space is reduced by the bytes used for alignment.
  96. *
  97. * @param __align A fundamental or extended alignment value.
  98. * @param __size Size of the aligned storage required.
  99. * @param __ptr Pointer to a buffer of @a __space bytes.
  100. * @param __space Size of the buffer pointed to by @a __ptr.
  101. * @return the updated pointer if the aligned storage fits, otherwise nullptr.
  102. */
  103. inline void*
  104. align(size_t __align, size_t __size, void*& __ptr, size_t& __space) noexcept
  105. {
  106. #ifdef _GLIBCXX_USE_C99_STDINT_TR1
  107. const auto __intptr = reinterpret_cast<uintptr_t>(__ptr);
  108. #else
  109. // Cannot use std::uintptr_t so assume that std::size_t can be used instead.
  110. static_assert(sizeof(size_t) >= sizeof(void*),
  111. "std::size_t must be a suitable substitute for std::uintptr_t");
  112. const auto __intptr = reinterpret_cast<unsigned long long>(__ptr);
  113. #endif
  114. const auto __aligned = (__intptr - 1u + __align) & -__align;
  115. const auto __diff = __aligned - __intptr;
  116. if ((__size + __diff) > __space)
  117. return nullptr;
  118. else
  119. {
  120. __space -= __diff;
  121. return __ptr = reinterpret_cast<void*>(__aligned);
  122. }
  123. }
  124. // 20.7.4 [util.dynamic.safety], pointer safety
  125. enum class pointer_safety { relaxed, preferred, strict };
  126. inline void
  127. declare_reachable(void*) { }
  128. template <typename _Tp>
  129. inline _Tp*
  130. undeclare_reachable(_Tp* __p) { return __p; }
  131. inline void
  132. declare_no_pointers(char*, size_t) { }
  133. inline void
  134. undeclare_no_pointers(char*, size_t) { }
  135. inline pointer_safety
  136. get_pointer_safety() noexcept { return pointer_safety::relaxed; }
  137. #if __cplusplus > 201703L
  138. /// Inform the compiler that a pointer is aligned.
  139. template<size_t _Align, class _Tp>
  140. [[nodiscard,__gnu__::__always_inline__]]
  141. constexpr _Tp* assume_aligned(_Tp* __ptr)
  142. {
  143. static_assert(std::ispow2(_Align));
  144. _GLIBCXX_DEBUG_ASSERT((std::uintptr_t)__ptr % _Align == 0);
  145. return static_cast<_Tp*>(__builtin_assume_aligned(__ptr, _Align));
  146. }
  147. #endif // C++2a
  148. #if __cplusplus > 201703L
  149. template<typename _Tp>
  150. struct __is_pair : false_type { };
  151. template<typename _Tp, typename _Up>
  152. struct __is_pair<pair<_Tp, _Up>> : true_type { };
  153. template<typename _Tp, typename _Up>
  154. struct __is_pair<const pair<_Tp, _Up>> : true_type { };
  155. template<typename _Tp, typename __ = _Require<__not_<__is_pair<_Tp>>>,
  156. typename _Alloc, typename... _Args>
  157. constexpr auto
  158. __uses_alloc_args(const _Alloc& __a, _Args&&... __args) noexcept
  159. {
  160. if constexpr (uses_allocator_v<remove_cv_t<_Tp>, _Alloc>)
  161. {
  162. if constexpr (is_constructible_v<_Tp, allocator_arg_t,
  163. const _Alloc&, _Args...>)
  164. {
  165. return tuple<allocator_arg_t, const _Alloc&, _Args&&...>(
  166. allocator_arg, __a, std::forward<_Args>(__args)...);
  167. }
  168. else
  169. {
  170. static_assert(is_constructible_v<_Tp, _Args..., const _Alloc&>,
  171. "construction with an allocator must be possible"
  172. " if uses_allocator is true");
  173. return tuple<_Args&&..., const _Alloc&>(
  174. std::forward<_Args>(__args)..., __a);
  175. }
  176. }
  177. else
  178. {
  179. static_assert(is_constructible_v<_Tp, _Args...>);
  180. return tuple<_Args&&...>(std::forward<_Args>(__args)...);
  181. }
  182. }
  183. #if __cpp_concepts
  184. template<typename _Tp>
  185. concept _Std_pair = __is_pair<_Tp>::value;
  186. #endif
  187. // This is a temporary workaround until -fconcepts is implied by -std=gnu++2a
  188. #if __cpp_concepts
  189. # define _GLIBCXX_STD_PAIR_CONSTRAINT(T) _Std_pair T
  190. # define _GLIBCXX_STD_PAIR_CONSTRAINT_(T) _Std_pair T
  191. #else
  192. # define _GLIBCXX_STD_PAIR_CONSTRAINT(T) \
  193. typename T, typename __ = _Require<__is_pair<T>>
  194. # define _GLIBCXX_STD_PAIR_CONSTRAINT_(T) typename T, typename
  195. #endif
  196. template<typename _Tp,
  197. #if ! __cpp_concepts
  198. typename __ = _Require<__not_<__is_pair<_Tp>>>,
  199. #endif
  200. typename _Alloc, typename... _Args>
  201. constexpr auto
  202. uses_allocator_construction_args(const _Alloc& __a,
  203. _Args&&... __args) noexcept
  204. #if __cpp_concepts
  205. requires (! _Std_pair<_Tp>)
  206. #endif
  207. {
  208. return std::__uses_alloc_args<_Tp>(__a, std::forward<_Args>(__args)...);
  209. }
  210. template<_GLIBCXX_STD_PAIR_CONSTRAINT(_Tp), typename _Alloc,
  211. typename _Tuple1, typename _Tuple2>
  212. constexpr auto
  213. uses_allocator_construction_args(const _Alloc& __a, piecewise_construct_t,
  214. _Tuple1&& __x, _Tuple2&& __y) noexcept;
  215. template<_GLIBCXX_STD_PAIR_CONSTRAINT(_Tp), typename _Alloc>
  216. constexpr auto
  217. uses_allocator_construction_args(const _Alloc&) noexcept;
  218. template<_GLIBCXX_STD_PAIR_CONSTRAINT(_Tp), typename _Alloc,
  219. typename _Up, typename _Vp>
  220. constexpr auto
  221. uses_allocator_construction_args(const _Alloc&, _Up&&, _Vp&&) noexcept;
  222. template<_GLIBCXX_STD_PAIR_CONSTRAINT(_Tp), typename _Alloc,
  223. typename _Up, typename _Vp>
  224. constexpr auto
  225. uses_allocator_construction_args(const _Alloc&,
  226. const pair<_Up, _Vp>&) noexcept;
  227. template<_GLIBCXX_STD_PAIR_CONSTRAINT(_Tp), typename _Alloc,
  228. typename _Up, typename _Vp>
  229. constexpr auto
  230. uses_allocator_construction_args(const _Alloc&, pair<_Up, _Vp>&&) noexcept;
  231. template<_GLIBCXX_STD_PAIR_CONSTRAINT_(_Tp), typename _Alloc,
  232. typename _Tuple1, typename _Tuple2>
  233. constexpr auto
  234. uses_allocator_construction_args(const _Alloc& __a, piecewise_construct_t,
  235. _Tuple1&& __x, _Tuple2&& __y) noexcept
  236. {
  237. using _Tp1 = typename _Tp::first_type;
  238. using _Tp2 = typename _Tp::second_type;
  239. return std::make_tuple(piecewise_construct,
  240. std::apply([&__a](auto&&... __args1) {
  241. return std::uses_allocator_construction_args<_Tp1>(
  242. __a, std::forward<decltype(__args1)>(__args1)...);
  243. }, std::forward<_Tuple1>(__x)),
  244. std::apply([&__a](auto&&... __args2) {
  245. return std::uses_allocator_construction_args<_Tp2>(
  246. __a, std::forward<decltype(__args2)>(__args2)...);
  247. }, std::forward<_Tuple2>(__y)));
  248. }
  249. template<_GLIBCXX_STD_PAIR_CONSTRAINT_(_Tp), typename _Alloc>
  250. constexpr auto
  251. uses_allocator_construction_args(const _Alloc& __a) noexcept
  252. {
  253. using _Tp1 = typename _Tp::first_type;
  254. using _Tp2 = typename _Tp::second_type;
  255. return std::make_tuple(piecewise_construct,
  256. std::uses_allocator_construction_args<_Tp1>(__a),
  257. std::uses_allocator_construction_args<_Tp2>(__a));
  258. }
  259. template<_GLIBCXX_STD_PAIR_CONSTRAINT_(_Tp), typename _Alloc,
  260. typename _Up, typename _Vp>
  261. constexpr auto
  262. uses_allocator_construction_args(const _Alloc& __a, _Up&& __u, _Vp&& __v)
  263. noexcept
  264. {
  265. using _Tp1 = typename _Tp::first_type;
  266. using _Tp2 = typename _Tp::second_type;
  267. return std::make_tuple(piecewise_construct,
  268. std::uses_allocator_construction_args<_Tp1>(__a,
  269. std::forward<_Up>(__u)),
  270. std::uses_allocator_construction_args<_Tp2>(__a,
  271. std::forward<_Vp>(__v)));
  272. }
  273. template<_GLIBCXX_STD_PAIR_CONSTRAINT_(_Tp), typename _Alloc,
  274. typename _Up, typename _Vp>
  275. constexpr auto
  276. uses_allocator_construction_args(const _Alloc& __a,
  277. const pair<_Up, _Vp>& __pr) noexcept
  278. {
  279. using _Tp1 = typename _Tp::first_type;
  280. using _Tp2 = typename _Tp::second_type;
  281. return std::make_tuple(piecewise_construct,
  282. std::uses_allocator_construction_args<_Tp1>(__a, __pr.first),
  283. std::uses_allocator_construction_args<_Tp2>(__a, __pr.second));
  284. }
  285. template<_GLIBCXX_STD_PAIR_CONSTRAINT_(_Tp), typename _Alloc,
  286. typename _Up, typename _Vp>
  287. constexpr auto
  288. uses_allocator_construction_args(const _Alloc& __a,
  289. pair<_Up, _Vp>&& __pr) noexcept
  290. {
  291. using _Tp1 = typename _Tp::first_type;
  292. using _Tp2 = typename _Tp::second_type;
  293. return std::make_tuple(piecewise_construct,
  294. std::uses_allocator_construction_args<_Tp1>(__a,
  295. std::move(__pr).first),
  296. std::uses_allocator_construction_args<_Tp2>(__a,
  297. std::move(__pr).second));
  298. }
  299. template<typename _Tp, typename _Alloc, typename... _Args>
  300. inline _Tp
  301. make_obj_using_allocator(const _Alloc& __a, _Args&&... __args)
  302. {
  303. return std::make_from_tuple<_Tp>(
  304. std::uses_allocator_construction_args<_Tp>(__a,
  305. std::forward<_Args>(__args)...));
  306. }
  307. template<typename _Tp, typename _Alloc, typename... _Args>
  308. inline _Tp*
  309. uninitialized_construct_using_allocator(_Tp* __p, const _Alloc& __a,
  310. _Args&&... __args)
  311. {
  312. void* __vp = const_cast<void*>(static_cast<const volatile void*>(__p));
  313. return ::new(__vp) _Tp(std::make_obj_using_allocator<_Tp>(__a,
  314. std::forward<_Args>(__args)...));
  315. }
  316. #endif // C++2a
  317. _GLIBCXX_END_NAMESPACE_VERSION
  318. } // namespace
  319. #endif // C++11
  320. #if __cplusplus > 201402L
  321. // Parallel STL algorithms
  322. # if __PSTL_EXECUTION_POLICIES_DEFINED
  323. // If <execution> has already been included, pull in implementations
  324. # include <pstl/glue_memory_impl.h>
  325. # else
  326. // Otherwise just pull in forward declarations
  327. # include <pstl/glue_memory_defs.h>
  328. # endif
  329. // Feature test macro for parallel algorithms
  330. # define __cpp_lib_parallel_algorithm 201603L
  331. #endif // C++17
  332. #endif /* _GLIBCXX_MEMORY */