local_counted_base.hpp 3.1 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148
  1. #ifndef BOOST_SMART_PTR_DETAIL_LOCAL_COUNTED_BASE_HPP_INCLUDED
  2. #define BOOST_SMART_PTR_DETAIL_LOCAL_COUNTED_BASE_HPP_INCLUDED
  3. // MS compatible compilers support #pragma once
  4. #if defined(_MSC_VER) && (_MSC_VER >= 1020)
  5. # pragma once
  6. #endif
  7. // detail/local_counted_base.hpp
  8. //
  9. // Copyright 2017 Peter Dimov
  10. //
  11. // Distributed under the Boost Software License, Version 1.0. (See
  12. // accompanying file LICENSE_1_0.txt or copy at
  13. // http://www.boost.org/LICENSE_1_0.txt)
  14. //
  15. // See http://www.boost.org/libs/smart_ptr/ for documentation.
  16. #include <boost/smart_ptr/detail/shared_count.hpp>
  17. #include <boost/config.hpp>
  18. #include <utility>
  19. namespace boost
  20. {
  21. namespace detail
  22. {
  23. class BOOST_SYMBOL_VISIBLE local_counted_base
  24. {
  25. private:
  26. local_counted_base & operator= ( local_counted_base const & );
  27. private:
  28. // not 'int' or 'unsigned' to avoid aliasing and enable optimizations
  29. enum count_type { min_ = 0, initial_ = 1, max_ = 2147483647 };
  30. count_type local_use_count_;
  31. public:
  32. BOOST_CONSTEXPR local_counted_base() BOOST_SP_NOEXCEPT: local_use_count_( initial_ )
  33. {
  34. }
  35. BOOST_CONSTEXPR local_counted_base( local_counted_base const & ) BOOST_SP_NOEXCEPT: local_use_count_( initial_ )
  36. {
  37. }
  38. virtual ~local_counted_base() /*BOOST_SP_NOEXCEPT*/
  39. {
  40. }
  41. virtual void local_cb_destroy() BOOST_SP_NOEXCEPT = 0;
  42. virtual boost::detail::shared_count local_cb_get_shared_count() const BOOST_SP_NOEXCEPT = 0;
  43. void add_ref() BOOST_SP_NOEXCEPT
  44. {
  45. #if !defined(__NVCC__)
  46. #if defined( __has_builtin )
  47. # if __has_builtin( __builtin_assume )
  48. __builtin_assume( local_use_count_ >= 1 );
  49. # endif
  50. #endif
  51. #endif
  52. local_use_count_ = static_cast<count_type>( local_use_count_ + 1 );
  53. }
  54. void release() BOOST_SP_NOEXCEPT
  55. {
  56. local_use_count_ = static_cast<count_type>( local_use_count_ - 1 );
  57. if( local_use_count_ == 0 )
  58. {
  59. local_cb_destroy();
  60. }
  61. }
  62. long local_use_count() const BOOST_SP_NOEXCEPT
  63. {
  64. return local_use_count_;
  65. }
  66. };
  67. class BOOST_SYMBOL_VISIBLE local_counted_impl: public local_counted_base
  68. {
  69. private:
  70. local_counted_impl( local_counted_impl const & );
  71. private:
  72. shared_count pn_;
  73. public:
  74. explicit local_counted_impl( shared_count const& pn ) BOOST_SP_NOEXCEPT: pn_( pn )
  75. {
  76. }
  77. #if !defined( BOOST_NO_CXX11_RVALUE_REFERENCES )
  78. explicit local_counted_impl( shared_count && pn ) BOOST_SP_NOEXCEPT: pn_( std::move(pn) )
  79. {
  80. }
  81. #endif
  82. virtual void local_cb_destroy() BOOST_SP_NOEXCEPT
  83. {
  84. delete this;
  85. }
  86. virtual boost::detail::shared_count local_cb_get_shared_count() const BOOST_SP_NOEXCEPT
  87. {
  88. return pn_;
  89. }
  90. };
  91. class BOOST_SYMBOL_VISIBLE local_counted_impl_em: public local_counted_base
  92. {
  93. public:
  94. shared_count pn_;
  95. virtual void local_cb_destroy() BOOST_SP_NOEXCEPT
  96. {
  97. shared_count().swap( pn_ );
  98. }
  99. virtual boost::detail::shared_count local_cb_get_shared_count() const BOOST_SP_NOEXCEPT
  100. {
  101. return pn_;
  102. }
  103. };
  104. } // namespace detail
  105. } // namespace boost
  106. #endif // #ifndef BOOST_SMART_PTR_DETAIL_LOCAL_COUNTED_BASE_HPP_INCLUDED