stl_construct.h 7.2 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236
  1. // nonstandard construct and destroy functions -*- C++ -*-
  2. // Copyright (C) 2001-2018 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. *
  22. * Copyright (c) 1994
  23. * Hewlett-Packard Company
  24. *
  25. * Permission to use, copy, modify, distribute and sell this software
  26. * and its documentation for any purpose is hereby granted without fee,
  27. * provided that the above copyright notice appear in all copies and
  28. * that both that copyright notice and this permission notice appear
  29. * in supporting documentation. Hewlett-Packard Company makes no
  30. * representations about the suitability of this software for any
  31. * purpose. It is provided "as is" without express or implied warranty.
  32. *
  33. *
  34. * Copyright (c) 1996,1997
  35. * Silicon Graphics Computer Systems, Inc.
  36. *
  37. * Permission to use, copy, modify, distribute and sell this software
  38. * and its documentation for any purpose is hereby granted without fee,
  39. * provided that the above copyright notice appear in all copies and
  40. * that both that copyright notice and this permission notice appear
  41. * in supporting documentation. Silicon Graphics makes no
  42. * representations about the suitability of this software for any
  43. * purpose. It is provided "as is" without express or implied warranty.
  44. */
  45. /** @file bits/stl_construct.h
  46. * This is an internal header file, included by other library headers.
  47. * Do not attempt to use it directly. @headername{memory}
  48. */
  49. #ifndef _STL_CONSTRUCT_H
  50. #define _STL_CONSTRUCT_H 1
  51. #include <new>
  52. #include <bits/move.h>
  53. #include <ext/alloc_traits.h>
  54. namespace std _GLIBCXX_VISIBILITY(default)
  55. {
  56. _GLIBCXX_BEGIN_NAMESPACE_VERSION
  57. /**
  58. * Constructs an object in existing memory by invoking an allocated
  59. * object's constructor with an initializer.
  60. */
  61. #if __cplusplus >= 201103L
  62. template<typename _T1, typename... _Args>
  63. inline void
  64. _Construct(_T1* __p, _Args&&... __args)
  65. { ::new(static_cast<void*>(__p)) _T1(std::forward<_Args>(__args)...); }
  66. #else
  67. template<typename _T1, typename _T2>
  68. inline void
  69. _Construct(_T1* __p, const _T2& __value)
  70. {
  71. // _GLIBCXX_RESOLVE_LIB_DEFECTS
  72. // 402. wrong new expression in [some_]allocator::construct
  73. ::new(static_cast<void*>(__p)) _T1(__value);
  74. }
  75. #endif
  76. template<typename _T1>
  77. inline void
  78. _Construct_novalue(_T1* __p)
  79. { ::new(static_cast<void*>(__p)) _T1; }
  80. /**
  81. * Destroy the object pointed to by a pointer type.
  82. */
  83. template<typename _Tp>
  84. inline void
  85. _Destroy(_Tp* __pointer)
  86. { __pointer->~_Tp(); }
  87. template<bool>
  88. struct _Destroy_aux
  89. {
  90. template<typename _ForwardIterator>
  91. static void
  92. __destroy(_ForwardIterator __first, _ForwardIterator __last)
  93. {
  94. for (; __first != __last; ++__first)
  95. std::_Destroy(std::__addressof(*__first));
  96. }
  97. };
  98. template<>
  99. struct _Destroy_aux<true>
  100. {
  101. template<typename _ForwardIterator>
  102. static void
  103. __destroy(_ForwardIterator, _ForwardIterator) { }
  104. };
  105. /**
  106. * Destroy a range of objects. If the value_type of the object has
  107. * a trivial destructor, the compiler should optimize all of this
  108. * away, otherwise the objects' destructors must be invoked.
  109. */
  110. template<typename _ForwardIterator>
  111. inline void
  112. _Destroy(_ForwardIterator __first, _ForwardIterator __last)
  113. {
  114. typedef typename iterator_traits<_ForwardIterator>::value_type
  115. _Value_type;
  116. #if __cplusplus >= 201103L
  117. // A deleted destructor is trivial, this ensures we reject such types:
  118. static_assert(is_destructible<_Value_type>::value,
  119. "value type is destructible");
  120. #endif
  121. std::_Destroy_aux<__has_trivial_destructor(_Value_type)>::
  122. __destroy(__first, __last);
  123. }
  124. template<bool>
  125. struct _Destroy_n_aux
  126. {
  127. template<typename _ForwardIterator, typename _Size>
  128. static _ForwardIterator
  129. __destroy_n(_ForwardIterator __first, _Size __count)
  130. {
  131. for (; __count > 0; (void)++__first, --__count)
  132. std::_Destroy(std::__addressof(*__first));
  133. return __first;
  134. }
  135. };
  136. template<>
  137. struct _Destroy_n_aux<true>
  138. {
  139. template<typename _ForwardIterator, typename _Size>
  140. static _ForwardIterator
  141. __destroy_n(_ForwardIterator __first, _Size __count)
  142. {
  143. std::advance(__first, __count);
  144. return __first;
  145. }
  146. };
  147. /**
  148. * Destroy a range of objects. If the value_type of the object has
  149. * a trivial destructor, the compiler should optimize all of this
  150. * away, otherwise the objects' destructors must be invoked.
  151. */
  152. template<typename _ForwardIterator, typename _Size>
  153. inline _ForwardIterator
  154. _Destroy_n(_ForwardIterator __first, _Size __count)
  155. {
  156. typedef typename iterator_traits<_ForwardIterator>::value_type
  157. _Value_type;
  158. #if __cplusplus >= 201103L
  159. // A deleted destructor is trivial, this ensures we reject such types:
  160. static_assert(is_destructible<_Value_type>::value,
  161. "value type is destructible");
  162. #endif
  163. return std::_Destroy_n_aux<__has_trivial_destructor(_Value_type)>::
  164. __destroy_n(__first, __count);
  165. }
  166. /**
  167. * Destroy a range of objects using the supplied allocator. For
  168. * nondefault allocators we do not optimize away invocation of
  169. * destroy() even if _Tp has a trivial destructor.
  170. */
  171. template<typename _ForwardIterator, typename _Allocator>
  172. void
  173. _Destroy(_ForwardIterator __first, _ForwardIterator __last,
  174. _Allocator& __alloc)
  175. {
  176. typedef __gnu_cxx::__alloc_traits<_Allocator> __traits;
  177. for (; __first != __last; ++__first)
  178. __traits::destroy(__alloc, std::__addressof(*__first));
  179. }
  180. template<typename _ForwardIterator, typename _Tp>
  181. inline void
  182. _Destroy(_ForwardIterator __first, _ForwardIterator __last,
  183. allocator<_Tp>&)
  184. {
  185. _Destroy(__first, __last);
  186. }
  187. #if __cplusplus > 201402L
  188. template <typename _Tp>
  189. inline void
  190. destroy_at(_Tp* __location)
  191. {
  192. std::_Destroy(__location);
  193. }
  194. template <typename _ForwardIterator>
  195. inline void
  196. destroy(_ForwardIterator __first, _ForwardIterator __last)
  197. {
  198. std::_Destroy(__first, __last);
  199. }
  200. template <typename _ForwardIterator, typename _Size>
  201. inline _ForwardIterator
  202. destroy_n(_ForwardIterator __first, _Size __count)
  203. {
  204. return std::_Destroy_n(__first, __count);
  205. }
  206. #endif
  207. _GLIBCXX_END_NAMESPACE_VERSION
  208. } // namespace std
  209. #endif /* _STL_CONSTRUCT_H */