View difference between Paste ID: XZaE2cnW and w1wSxbuf
SHOW: | | - or go back to the newest paste.
1
/** @file stl/fast_pointer_cast.hpp
2
***
3
*** @brief
4
***     Smart pointer casts with move semantics based optimization. @n
5
***     (If you are casting temporary smart pointer it will be moved-and-casted into
6
***      new pointer using lock free mechanism).
7
**/
8
9
#pragma once
10
11
#include <memory>
12
13
namespace stl
14
{
15-
	//! Dummy struct used to specialize shared_ptr constructor.
15+
	//! Dummy struct used to specialize std::shared_ptr base class.
16
	struct fast_static_pointer_cast__access_hack_tag
17
	{
18
	};
19
20
} // namespace stl
21
22
namespace std
23
{
24
	namespace tr1
25
	{
26
		//! This specialization used to invoke some internal shared_ptr stuff.
27
		/** std::_Ptr_base treats this specialization as friend. */
28
		template<>
29
		class _Ptr_base< ::stl::fast_static_pointer_cast__access_hack_tag >
30
		{
31
		public:
32
33
			template< class T, class U >
34
			static void DoConstCastTransfer( _Ptr_base< T > &rTarget, _Ptr_base< U > &&rrSource )
35
			{
36
				// Cast and transfer pointer
37
				rTarget._Ptr  = const_cast< T * >( rrSource._Ptr );
38
				rTarget._Rep  = rrSource._Rep;
39
40
				// Invalidate source
41
				rrSource._Ptr = nullptr;
42
				rrSource._Rep = nullptr;
43
			}
44
45
			template< class T, class U >
46
			static void DoStaticCastTransfer( _Ptr_base< T > &rTarget, _Ptr_base< U > &&rrSource )
47
			{
48
				// Cast and transfer pointer
49
				rTarget._Ptr  = static_cast< T * >( rrSource._Ptr );
50
				rTarget._Rep  = rrSource._Rep;
51
52
				// Invalidate source
53
				rrSource._Ptr = nullptr;
54
				rrSource._Rep = nullptr;
55
			}
56
57
			template< class T, class U >
58
			static void DoDynamicCastTransfer( _Ptr_base< T > &rTarget, _Ptr_base< U > &&rrSource )
59
			{
60
				// Cast and transfer pointer
61
				rTarget._Ptr  = dynamic_cast< T * >( rrSource._Ptr );
62
				rTarget._Rep  = rrSource._Rep;
63
64
				// Invalidate source
65
				rrSource._Ptr = nullptr;
66
				rrSource._Rep = nullptr;
67
			}
68
		};
69
70
	} // namespace tr1
71
72
} // namespace std
73
74
namespace stl
75
{
76
	//! Implements fast static_pointer_cast for rvalue references (without atomic instructions).
77
	/** This variant is used for rvalue references, this variant applies lock free optimization. */
78
	template< class T, class U >
79
	inline std::shared_ptr< T > fast_static_pointer_cast( std::shared_ptr< U > &&rrp )
80
	{
81
		std::shared_ptr< T > pRes;
82
83
		std::tr1::_Ptr_base< fast_static_pointer_cast__access_hack_tag >::DoStaticCastTransfer( pRes, std::move( rrp ) );
84
85
		return std::move( pRes );
86
	}
87
88
	//! Implements fast static_pointer_cast for rvalue references (without atomic instructions).
89
	/** This variant is used for lvalue references and just calls slow std implementation. */
90
	template< class T, class U >
91
	inline std::shared_ptr< T > fast_static_pointer_cast( const std::shared_ptr< U > &rrp )
92
	{
93-
		return stl::fast_static_pointer_cast< T >( rrp );
93+
		return std::static_pointer_cast< T >( rrp );
94
	}
95
96
	//! Implements fast dynamic_pointer_cast for rvalue references (without atomic instructions).
97
	/** This variant is used for rvalue references, this variant applies lock free optimization. */
98
	template< class T, class U >
99
	inline std::shared_ptr< T > fast_dynamic_pointer_cast( std::shared_ptr< U > &&rrp )
100
	{
101
		std::shared_ptr< T > pRes;
102
103
		std::tr1::_Ptr_base< fast_static_pointer_cast__access_hack_tag >::DoDynamicCastTransfer( pRes, std::move( rrp ) );
104
105
		return std::move( pRes );
106
	}
107
108
	//! Implements fast dynamic_pointer_cast for rvalue references (without atomic instructions).
109
	/** This variant is used for lvalue references and just calls slow std implementation. */
110
	template< class T, class U >
111
	inline std::shared_ptr< T > fast_dynamic_pointer_cast( const std::shared_ptr< U > &rrp )
112
	{
113-
		return stl::fast_static_pointer_cast< T >( rrp );
113+
		return std::static_pointer_cast< T >( rrp );
114
	}
115
116
	//! Implements fast const_pointer_cast for rvalue references (without atomic instructions).
117
	/** This variant is used for rvalue references, this variant applies lock free optimization. */
118
	template< class T, class U >
119
	inline std::shared_ptr< T > fast_const_pointer_cast( std::shared_ptr< U > &&rrp )
120
	{
121
		std::shared_ptr< T > pRes;
122
123
		std::tr1::_Ptr_base< fast_static_pointer_cast__access_hack_tag >::DoConstCastTransfer( pRes, std::move( rrp ) );
124
125
		return std::move( pRes );
126
	}
127
128
	//! Implements fast const_pointer_cast for rvalue references (without atomic instructions).
129
	/** This variant is used for lvalue references and just calls slow std implementation. */
130
	template< class T, class U >
131
	inline std::shared_ptr< T > fast_const_pointer_cast( const std::shared_ptr< U > &rrp )
132
	{
133-
		return stl::fast_static_pointer_cast< T >( rrp );
133+
		return std::static_pointer_cast< T >( rrp );
134
	}
135
136
} // namespace stl