LCOV - code coverage report
Current view: top level - v1/__memory - allocator.h (source / functions) Coverage Total Hit
Test: vrml_claude.info Lines: 82.6 % 23 19
Test Date: 2024-03-08 16:33:03 Functions: 79.4 % 68 54

            Line data    Source code
       1              : // -*- C++ -*-
       2              : //===----------------------------------------------------------------------===//
       3              : //
       4              : // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
       5              : // See https://llvm.org/LICENSE.txt for license information.
       6              : // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
       7              : //
       8              : //===----------------------------------------------------------------------===//
       9              : 
      10              : #ifndef _LIBCPP___MEMORY_ALLOCATOR_H
      11              : #define _LIBCPP___MEMORY_ALLOCATOR_H
      12              : 
      13              : #include <__config>
      14              : #include <__memory/allocate_at_least.h>
      15              : #include <__memory/allocator_traits.h>
      16              : #include <__type_traits/is_constant_evaluated.h>
      17              : #include <__type_traits/is_same.h>
      18              : #include <__type_traits/is_void.h>
      19              : #include <__type_traits/is_volatile.h>
      20              : #include <__utility/forward.h>
      21              : #include <cstddef>
      22              : #include <new>
      23              : #include <stdexcept>
      24              : 
      25              : #if !defined(_LIBCPP_HAS_NO_PRAGMA_SYSTEM_HEADER)
      26              : #  pragma GCC system_header
      27              : #endif
      28              : 
      29              : _LIBCPP_BEGIN_NAMESPACE_STD
      30              : 
      31              : template <class _Tp> class allocator;
      32              : 
      33              : #if _LIBCPP_STD_VER <= 17 || defined(_LIBCPP_ENABLE_CXX20_REMOVED_ALLOCATOR_VOID_SPECIALIZATION)
      34              : // These specializations shouldn't be marked _LIBCPP_DEPRECATED_IN_CXX17.
      35              : // Specializing allocator<void> is deprecated, but not using it.
      36              : template <>
      37              : class _LIBCPP_TEMPLATE_VIS allocator<void>
      38              : {
      39              : #if _LIBCPP_STD_VER <= 17 || defined(_LIBCPP_ENABLE_CXX20_REMOVED_ALLOCATOR_MEMBERS)
      40              : public:
      41              :     _LIBCPP_DEPRECATED_IN_CXX17 typedef void*             pointer;
      42              :     _LIBCPP_DEPRECATED_IN_CXX17 typedef const void*       const_pointer;
      43              :     _LIBCPP_DEPRECATED_IN_CXX17 typedef void              value_type;
      44              : 
      45              :     template <class _Up> struct _LIBCPP_DEPRECATED_IN_CXX17 rebind {typedef allocator<_Up> other;};
      46              : #endif
      47              : };
      48              : 
      49              : template <>
      50              : class _LIBCPP_TEMPLATE_VIS allocator<const void>
      51              : {
      52              : #if _LIBCPP_STD_VER <= 17 || defined(_LIBCPP_ENABLE_CXX20_REMOVED_ALLOCATOR_MEMBERS)
      53              : public:
      54              :     _LIBCPP_DEPRECATED_IN_CXX17 typedef const void*       pointer;
      55              :     _LIBCPP_DEPRECATED_IN_CXX17 typedef const void*       const_pointer;
      56              :     _LIBCPP_DEPRECATED_IN_CXX17 typedef const void        value_type;
      57              : 
      58              :     template <class _Up> struct _LIBCPP_DEPRECATED_IN_CXX17 rebind {typedef allocator<_Up> other;};
      59              : #endif
      60              : };
      61              : #endif
      62              : 
      63              : // This class provides a non-trivial default constructor to the class that derives from it
      64              : // if the condition is satisfied.
      65              : //
      66              : // The second template parameter exists to allow giving a unique type to __non_trivial_if,
      67              : // which makes it possible to avoid breaking the ABI when making this a base class of an
      68              : // existing class. Without that, imagine we have classes D1 and D2, both of which used to
      69              : // have no base classes, but which now derive from __non_trivial_if. The layout of a class
      70              : // that inherits from both D1 and D2 will change because the two __non_trivial_if base
      71              : // classes are not allowed to share the same address.
      72              : //
      73              : // By making those __non_trivial_if base classes unique, we work around this problem and
      74              : // it is safe to start deriving from __non_trivial_if in existing classes.
      75              : template <bool _Cond, class _Unique>
      76              : struct __non_trivial_if { };
      77              : 
      78              : template <class _Unique>
      79              : struct __non_trivial_if<true, _Unique> {
      80              :     _LIBCPP_INLINE_VISIBILITY
      81      2371829 :     _LIBCPP_CONSTEXPR __non_trivial_if() _NOEXCEPT { }
      82              : };
      83              : 
      84              : // allocator
      85              : //
      86              : // Note: For ABI compatibility between C++20 and previous standards, we make
      87              : //       allocator<void> trivial in C++20.
      88              : 
      89              : template <class _Tp>
      90              : class _LIBCPP_TEMPLATE_VIS allocator
      91              :     : private __non_trivial_if<!is_void<_Tp>::value, allocator<_Tp> >
      92              : {
      93              :     static_assert(!is_volatile<_Tp>::value, "std::allocator does not support volatile types");
      94              : public:
      95              :     typedef size_t      size_type;
      96              :     typedef ptrdiff_t   difference_type;
      97              :     typedef _Tp         value_type;
      98              :     typedef true_type   propagate_on_container_move_assignment;
      99              :     typedef true_type   is_always_equal;
     100              : 
     101              :     _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_SINCE_CXX20
     102      2830238 :     allocator() _NOEXCEPT = default;
     103              : 
     104              :     template <class _Up>
     105              :     _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_SINCE_CXX20
     106              :     allocator(const allocator<_Up>&) _NOEXCEPT { }
     107              : 
     108              :     _LIBCPP_NODISCARD_AFTER_CXX17 _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_SINCE_CXX20
     109        56174 :     _Tp* allocate(size_t __n) {
     110        56174 :         if (__n > allocator_traits<allocator>::max_size(*this))
     111            0 :             __throw_bad_array_new_length();
     112        56174 :         if (__libcpp_is_constant_evaluated()) {
     113            0 :             return static_cast<_Tp*>(::operator new(__n * sizeof(_Tp)));
     114              :         } else {
     115        56174 :             return static_cast<_Tp*>(_VSTD::__libcpp_allocate(__n * sizeof(_Tp), _LIBCPP_ALIGNOF(_Tp)));
     116              :         }
     117        56174 :     }
     118              : 
     119              : #if _LIBCPP_STD_VER > 20
     120              :     [[nodiscard]] _LIBCPP_HIDE_FROM_ABI constexpr
     121              :     allocation_result<_Tp*> allocate_at_least(size_t __n) {
     122              :         return {allocate(__n), __n};
     123              :     }
     124              : #endif
     125              : 
     126              :     _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_SINCE_CXX20
     127        28378 :     void deallocate(_Tp* __p, size_t __n) _NOEXCEPT {
     128        28378 :         if (__libcpp_is_constant_evaluated()) {
     129            0 :             ::operator delete(__p);
     130            0 :         } else {
     131        28378 :             _VSTD::__libcpp_deallocate((void*)__p, __n * sizeof(_Tp), _LIBCPP_ALIGNOF(_Tp));
     132              :         }
     133        28378 :     }
     134              : 
     135              :     // C++20 Removed members
     136              : #if _LIBCPP_STD_VER <= 17 || defined(_LIBCPP_ENABLE_CXX20_REMOVED_ALLOCATOR_MEMBERS)
     137              :     _LIBCPP_DEPRECATED_IN_CXX17 typedef _Tp*       pointer;
     138              :     _LIBCPP_DEPRECATED_IN_CXX17 typedef const _Tp* const_pointer;
     139              :     _LIBCPP_DEPRECATED_IN_CXX17 typedef _Tp&       reference;
     140              :     _LIBCPP_DEPRECATED_IN_CXX17 typedef const _Tp& const_reference;
     141              : 
     142              :     template <class _Up>
     143              :     struct _LIBCPP_DEPRECATED_IN_CXX17 rebind {
     144              :         typedef allocator<_Up> other;
     145              :     };
     146              : 
     147              :     _LIBCPP_DEPRECATED_IN_CXX17 _LIBCPP_INLINE_VISIBILITY
     148              :     pointer address(reference __x) const _NOEXCEPT {
     149              :         return _VSTD::addressof(__x);
     150              :     }
     151              :     _LIBCPP_DEPRECATED_IN_CXX17 _LIBCPP_INLINE_VISIBILITY
     152              :     const_pointer address(const_reference __x) const _NOEXCEPT {
     153              :         return _VSTD::addressof(__x);
     154              :     }
     155              : 
     156              :     _LIBCPP_NODISCARD_AFTER_CXX17 _LIBCPP_INLINE_VISIBILITY _LIBCPP_DEPRECATED_IN_CXX17
     157              :     _Tp* allocate(size_t __n, const void*) {
     158              :         return allocate(__n);
     159              :     }
     160              : 
     161      4704632 :     _LIBCPP_DEPRECATED_IN_CXX17 _LIBCPP_INLINE_VISIBILITY size_type max_size() const _NOEXCEPT {
     162      4704632 :         return size_type(~0) / sizeof(_Tp);
     163              :     }
     164              : 
     165              :     template <class _Up, class... _Args>
     166              :     _LIBCPP_DEPRECATED_IN_CXX17 _LIBCPP_INLINE_VISIBILITY
     167       565406 :     void construct(_Up* __p, _Args&&... __args) {
     168       565406 :         ::new ((void*)__p) _Up(_VSTD::forward<_Args>(__args)...);
     169       565406 :     }
     170              : 
     171              :     _LIBCPP_DEPRECATED_IN_CXX17 _LIBCPP_INLINE_VISIBILITY
     172       545510 :     void destroy(pointer __p) {
     173       545510 :         __p->~_Tp();
     174       545510 :     }
     175              : #endif
     176              : };
     177              : 
     178              : template <class _Tp>
     179              : class _LIBCPP_TEMPLATE_VIS allocator<const _Tp>
     180              :     : private __non_trivial_if<!is_void<_Tp>::value, allocator<const _Tp> >
     181              : {
     182              :     static_assert(!is_volatile<_Tp>::value, "std::allocator does not support volatile types");
     183              : public:
     184              :     typedef size_t      size_type;
     185              :     typedef ptrdiff_t   difference_type;
     186              :     typedef const _Tp   value_type;
     187              :     typedef true_type   propagate_on_container_move_assignment;
     188              :     typedef true_type   is_always_equal;
     189              : 
     190              :     _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_SINCE_CXX20
     191              :     allocator() _NOEXCEPT = default;
     192              : 
     193              :     template <class _Up>
     194              :     _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_SINCE_CXX20
     195              :     allocator(const allocator<_Up>&) _NOEXCEPT { }
     196              : 
     197              :     _LIBCPP_NODISCARD_AFTER_CXX17 _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_SINCE_CXX20
     198              :     const _Tp* allocate(size_t __n) {
     199              :         if (__n > allocator_traits<allocator>::max_size(*this))
     200              :             __throw_bad_array_new_length();
     201              :         if (__libcpp_is_constant_evaluated()) {
     202              :             return static_cast<const _Tp*>(::operator new(__n * sizeof(_Tp)));
     203              :         } else {
     204              :             return static_cast<const _Tp*>(_VSTD::__libcpp_allocate(__n * sizeof(_Tp), _LIBCPP_ALIGNOF(_Tp)));
     205              :         }
     206              :     }
     207              : 
     208              : #if _LIBCPP_STD_VER > 20
     209              :     [[nodiscard]] _LIBCPP_HIDE_FROM_ABI constexpr
     210              :     allocation_result<const _Tp*> allocate_at_least(size_t __n) {
     211              :         return {allocate(__n), __n};
     212              :     }
     213              : #endif
     214              : 
     215              :     _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_SINCE_CXX20
     216              :     void deallocate(const _Tp* __p, size_t __n) {
     217              :         if (__libcpp_is_constant_evaluated()) {
     218              :             ::operator delete(const_cast<_Tp*>(__p));
     219              :         } else {
     220              :             _VSTD::__libcpp_deallocate((void*) const_cast<_Tp *>(__p), __n * sizeof(_Tp), _LIBCPP_ALIGNOF(_Tp));
     221              :         }
     222              :     }
     223              : 
     224              :     // C++20 Removed members
     225              : #if _LIBCPP_STD_VER <= 17 || defined(_LIBCPP_ENABLE_CXX20_REMOVED_ALLOCATOR_MEMBERS)
     226              :     _LIBCPP_DEPRECATED_IN_CXX17 typedef const _Tp* pointer;
     227              :     _LIBCPP_DEPRECATED_IN_CXX17 typedef const _Tp* const_pointer;
     228              :     _LIBCPP_DEPRECATED_IN_CXX17 typedef const _Tp& reference;
     229              :     _LIBCPP_DEPRECATED_IN_CXX17 typedef const _Tp& const_reference;
     230              : 
     231              :     template <class _Up>
     232              :     struct _LIBCPP_DEPRECATED_IN_CXX17 rebind {
     233              :         typedef allocator<_Up> other;
     234              :     };
     235              : 
     236              :     _LIBCPP_DEPRECATED_IN_CXX17 _LIBCPP_INLINE_VISIBILITY
     237              :     const_pointer address(const_reference __x) const _NOEXCEPT {
     238              :         return _VSTD::addressof(__x);
     239              :     }
     240              : 
     241              :     _LIBCPP_NODISCARD_AFTER_CXX17 _LIBCPP_INLINE_VISIBILITY _LIBCPP_DEPRECATED_IN_CXX17
     242              :     const _Tp* allocate(size_t __n, const void*) {
     243              :         return allocate(__n);
     244              :     }
     245              : 
     246              :     _LIBCPP_DEPRECATED_IN_CXX17 _LIBCPP_INLINE_VISIBILITY size_type max_size() const _NOEXCEPT {
     247              :         return size_type(~0) / sizeof(_Tp);
     248              :     }
     249              : 
     250              :     template <class _Up, class... _Args>
     251              :     _LIBCPP_DEPRECATED_IN_CXX17 _LIBCPP_INLINE_VISIBILITY
     252              :     void construct(_Up* __p, _Args&&... __args) {
     253              :         ::new ((void*)__p) _Up(_VSTD::forward<_Args>(__args)...);
     254              :     }
     255              : 
     256              :     _LIBCPP_DEPRECATED_IN_CXX17 _LIBCPP_INLINE_VISIBILITY
     257              :     void destroy(pointer __p) {
     258              :         __p->~_Tp();
     259              :     }
     260              : #endif
     261              : };
     262              : 
     263              : template <class _Tp, class _Up>
     264              : inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_SINCE_CXX20
     265              : bool operator==(const allocator<_Tp>&, const allocator<_Up>&) _NOEXCEPT {return true;}
     266              : 
     267              : template <class _Tp, class _Up>
     268              : inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_SINCE_CXX20
     269              : bool operator!=(const allocator<_Tp>&, const allocator<_Up>&) _NOEXCEPT {return false;}
     270              : 
     271              : _LIBCPP_END_NAMESPACE_STD
     272              : 
     273              : #endif // _LIBCPP___MEMORY_ALLOCATOR_H
        

Generated by: LCOV version 2.0-1