Back to home page

EIC code displayed by LXR

 
 

    


File indexing completed on 2025-09-16 08:49:57

0001 #ifndef BOOST_SMART_PTR_DETAIL_SP_COUNTED_IMPL_HPP_INCLUDED
0002 #define BOOST_SMART_PTR_DETAIL_SP_COUNTED_IMPL_HPP_INCLUDED
0003 
0004 // MS compatible compilers support #pragma once
0005 
0006 #if defined(_MSC_VER) && (_MSC_VER >= 1020)
0007 # pragma once
0008 #endif
0009 
0010 //
0011 //  detail/sp_counted_impl.hpp
0012 //
0013 //  Copyright (c) 2001, 2002, 2003 Peter Dimov and Multi Media Ltd.
0014 //  Copyright 2004-2005 Peter Dimov
0015 //
0016 // Distributed under the Boost Software License, Version 1.0. (See
0017 // accompanying file LICENSE_1_0.txt or copy at
0018 // http://www.boost.org/LICENSE_1_0.txt)
0019 //
0020 
0021 #if defined(BOOST_SP_USE_STD_ALLOCATOR) && defined(BOOST_SP_USE_QUICK_ALLOCATOR)
0022 # error BOOST_SP_USE_STD_ALLOCATOR and BOOST_SP_USE_QUICK_ALLOCATOR are incompatible.
0023 #endif
0024 
0025 #include <boost/smart_ptr/detail/sp_counted_base.hpp>
0026 #include <boost/smart_ptr/detail/deprecated_macros.hpp>
0027 #include <boost/core/checked_delete.hpp>
0028 #include <boost/core/addressof.hpp>
0029 #include <boost/config.hpp>
0030 
0031 #if defined(BOOST_SP_USE_QUICK_ALLOCATOR)
0032 #include <boost/smart_ptr/detail/quick_allocator.hpp>
0033 #endif
0034 
0035 #include <memory>           // std::allocator, std::allocator_traits
0036 #include <cstddef>          // std::size_t
0037 
0038 namespace boost
0039 {
0040 
0041 #if defined(BOOST_SP_ENABLE_DEBUG_HOOKS)
0042 
0043 void sp_scalar_constructor_hook( void * px, std::size_t size, void * pn );
0044 void sp_scalar_destructor_hook( void * px, std::size_t size, void * pn );
0045 
0046 #endif
0047 
0048 namespace detail
0049 {
0050 
0051 // get_local_deleter
0052 
0053 template<class D> class local_sp_deleter;
0054 
0055 template<class D> D * get_local_deleter( D * /*p*/ ) noexcept
0056 {
0057     return 0;
0058 }
0059 
0060 template<class D> D * get_local_deleter( local_sp_deleter<D> * p ) noexcept;
0061 
0062 //
0063 
0064 template<class X> class BOOST_SYMBOL_VISIBLE sp_counted_impl_p: public sp_counted_base
0065 {
0066 private:
0067 
0068     X * px_;
0069 
0070     sp_counted_impl_p( sp_counted_impl_p const & );
0071     sp_counted_impl_p & operator= ( sp_counted_impl_p const & );
0072 
0073     typedef sp_counted_impl_p<X> this_type;
0074 
0075 public:
0076 
0077     explicit sp_counted_impl_p( X * px ): px_( px )
0078     {
0079 #if defined(BOOST_SP_ENABLE_DEBUG_HOOKS)
0080         boost::sp_scalar_constructor_hook( px, sizeof(X), this );
0081 #endif
0082     }
0083 
0084     void dispose() noexcept override
0085     {
0086 #if defined(BOOST_SP_ENABLE_DEBUG_HOOKS)
0087         boost::sp_scalar_destructor_hook( px_, sizeof(X), this );
0088 #endif
0089         boost::checked_delete( px_ );
0090     }
0091 
0092     void * get_deleter( sp_typeinfo_ const & ) noexcept override
0093     {
0094         return 0;
0095     }
0096 
0097     void * get_local_deleter( sp_typeinfo_ const & ) noexcept override
0098     {
0099         return 0;
0100     }
0101 
0102     void * get_untyped_deleter() noexcept override
0103     {
0104         return 0;
0105     }
0106 
0107 #if defined(BOOST_SP_USE_STD_ALLOCATOR)
0108 
0109     void * operator new( std::size_t )
0110     {
0111         return std::allocator<this_type>().allocate( 1, static_cast<this_type *>(0) );
0112     }
0113 
0114     void operator delete( void * p )
0115     {
0116         std::allocator<this_type>().deallocate( static_cast<this_type *>(p), 1 );
0117     }
0118 
0119 #endif
0120 
0121 #if defined(BOOST_SP_USE_QUICK_ALLOCATOR)
0122 
0123     void * operator new( std::size_t )
0124     {
0125         return quick_allocator<this_type>::alloc();
0126     }
0127 
0128     void operator delete( void * p )
0129     {
0130         quick_allocator<this_type>::dealloc( p );
0131     }
0132 
0133 #endif
0134 };
0135 
0136 template<class P, class D> class BOOST_SYMBOL_VISIBLE sp_counted_impl_pd: public sp_counted_base
0137 {
0138 private:
0139 
0140     P ptr; // copy constructor must not throw
0141     D del; // copy/move constructor must not throw
0142 
0143     sp_counted_impl_pd( sp_counted_impl_pd const & );
0144     sp_counted_impl_pd & operator= ( sp_counted_impl_pd const & );
0145 
0146     typedef sp_counted_impl_pd<P, D> this_type;
0147 
0148 public:
0149 
0150     // pre: d(p) must not throw
0151 
0152     sp_counted_impl_pd( P p, D & d ): ptr( p ), del( static_cast< D&& >( d ) )
0153     {
0154     }
0155 
0156     sp_counted_impl_pd( P p ): ptr( p ), del()
0157     {
0158     }
0159 
0160     void dispose() noexcept override
0161     {
0162         del( ptr );
0163     }
0164 
0165     void * get_deleter( sp_typeinfo_ const & ti ) noexcept override
0166     {
0167         return ti == BOOST_SP_TYPEID_(D)? &reinterpret_cast<char&>( del ): 0;
0168     }
0169 
0170     void * get_local_deleter( sp_typeinfo_ const & ti ) noexcept override
0171     {
0172         return ti == BOOST_SP_TYPEID_(D)? boost::detail::get_local_deleter( boost::addressof( del ) ): 0;
0173     }
0174 
0175     void * get_untyped_deleter() noexcept override
0176     {
0177         return &reinterpret_cast<char&>( del );
0178     }
0179 
0180 #if defined(BOOST_SP_USE_STD_ALLOCATOR)
0181 
0182     void * operator new( std::size_t )
0183     {
0184         return std::allocator<this_type>().allocate( 1, static_cast<this_type *>(0) );
0185     }
0186 
0187     void operator delete( void * p )
0188     {
0189         std::allocator<this_type>().deallocate( static_cast<this_type *>(p), 1 );
0190     }
0191 
0192 #endif
0193 
0194 #if defined(BOOST_SP_USE_QUICK_ALLOCATOR)
0195 
0196     void * operator new( std::size_t )
0197     {
0198         return quick_allocator<this_type>::alloc();
0199     }
0200 
0201     void operator delete( void * p )
0202     {
0203         quick_allocator<this_type>::dealloc( p );
0204     }
0205 
0206 #endif
0207 };
0208 
0209 template<class P, class D, class A> class BOOST_SYMBOL_VISIBLE sp_counted_impl_pda: public sp_counted_base
0210 {
0211 private:
0212 
0213     P p_; // copy constructor must not throw
0214     D d_; // copy/move constructor must not throw
0215     A a_; // copy constructor must not throw
0216 
0217     sp_counted_impl_pda( sp_counted_impl_pda const & );
0218     sp_counted_impl_pda & operator= ( sp_counted_impl_pda const & );
0219 
0220     typedef sp_counted_impl_pda<P, D, A> this_type;
0221 
0222 public:
0223 
0224     // pre: d( p ) must not throw
0225 
0226     sp_counted_impl_pda( P p, D & d, A a ): p_( p ), d_( static_cast< D&& >( d ) ), a_( a )
0227     {
0228     }
0229 
0230     sp_counted_impl_pda( P p, A a ): p_( p ), d_( a ), a_( a )
0231     {
0232     }
0233 
0234     void dispose() noexcept override
0235     {
0236         d_( p_ );
0237     }
0238 
0239     void destroy() noexcept override
0240     {
0241         typedef typename std::allocator_traits<A>::template rebind_alloc< this_type > A2;
0242 
0243         A2 a2( a_ );
0244 
0245         this->~this_type();
0246 
0247         a2.deallocate( this, 1 );
0248     }
0249 
0250     void * get_deleter( sp_typeinfo_ const & ti ) noexcept override
0251     {
0252         return ti == BOOST_SP_TYPEID_( D )? &reinterpret_cast<char&>( d_ ): 0;
0253     }
0254 
0255     void * get_local_deleter( sp_typeinfo_ const & ti ) noexcept override
0256     {
0257         return ti == BOOST_SP_TYPEID_( D )? boost::detail::get_local_deleter( boost::addressof( d_ ) ): 0;
0258     }
0259 
0260     void * get_untyped_deleter() noexcept override
0261     {
0262         return &reinterpret_cast<char&>( d_ );
0263     }
0264 };
0265 
0266 } // namespace detail
0267 
0268 } // namespace boost
0269 
0270 #endif  // #ifndef BOOST_SMART_PTR_DETAIL_SP_COUNTED_IMPL_HPP_INCLUDED