proxygen
folly::DiscriminatedPtr< Types > Class Template Reference

#include <DiscriminatedPtr.h>

Public Member Functions

 DiscriminatedPtr ()
 
template<typename T >
 DiscriminatedPtr (T *ptr)
 
template<typename T >
void set (T *ptr)
 
template<typename T >
Tget_nothrow () noexcept
 
template<typename T >
const Tget_nothrow () const noexcept
 
template<typename T >
Tget ()
 
template<typename T >
const Tget () const
 
bool empty () const
 
template<typename T >
bool hasType () const
 
void clear ()
 
template<typename T >
DiscriminatedPtroperator= (T *ptr)
 
template<typename V >
dptr_detail::VisitorResult< V, Types... >::type apply (V &&visitor)
 
template<typename V >
dptr_detail::ConstVisitorResult< V, Types... >::type apply (V &&visitor) const
 

Private Member Functions

template<typename T >
uint16_t typeIndex () const
 
uint16_t index () const
 
void * ptr () const
 
void set (void *p, uint16_t v)
 

Private Attributes

uintptr_t data_
 

Detailed Description

template<typename... Types>
class folly::DiscriminatedPtr< Types >

Discriminated pointer.

Given a list of types, a DiscriminatedPtr<Types...> may point to an object of one of the given types, or may be empty. DiscriminatedPtr is type-safe: you may only get a pointer to the type that you put in, otherwise get throws an exception (and get_nothrow returns nullptr)

This pointer does not do any kind of lifetime management – it's not a "smart" pointer. You are responsible for deallocating any memory used to hold pointees, if necessary.

Definition at line 57 of file DiscriminatedPtr.h.

Constructor & Destructor Documentation

template<typename... Types>
folly::DiscriminatedPtr< Types >::DiscriminatedPtr ( )
inline

Create an empty DiscriminatedPtr.

Definition at line 67 of file DiscriminatedPtr.h.

67 : data_(0) {}
template<typename... Types>
template<typename T >
folly::DiscriminatedPtr< Types >::DiscriminatedPtr ( T ptr)
inlineexplicit

Create a DiscriminatedPtr that points to an object of type T. Fails at compile time if T is not a valid type (listed in Types)

Definition at line 74 of file DiscriminatedPtr.h.

References folly::DiscriminatedPtr< Types >::ptr().

74  {
75  set(ptr, typeIndex<T>());
76  }

Member Function Documentation

template<typename... Types>
template<typename V >
dptr_detail::VisitorResult<V, Types...>::type folly::DiscriminatedPtr< Types >::apply ( V &&  visitor)
inline

Apply a visitor to this object, calling the appropriate overload for the type currently stored in DiscriminatedPtr. Throws invalid_argument if the DiscriminatedPtr is empty.

The visitor must meet the following requirements:

  • The visitor must allow invocation as a function by overloading operator(), unambiguously accepting all values of type T* (or const T*) for all T in Types...
  • All operations of the function object on T* (or const T*) must return the same type (or a static_assert will fire).

Definition at line 174 of file DiscriminatedPtr.h.

References folly::DiscriminatedPtr< Types >::index(), and folly::DiscriminatedPtr< Types >::ptr().

174  {
175  size_t n = index();
176  if (n == 0) {
177  throw std::invalid_argument("Empty DiscriminatedPtr");
178  }
179  return dptr_detail::ApplyVisitor<V, Types...>()(
180  n, std::forward<V>(visitor), ptr());
181  }
ApplyVisitor1< sizeof...(Types), V, typename VisitorResult< V, Types... >::type, Types... > ApplyVisitor
uint16_t index() const
template<typename... Types>
template<typename V >
dptr_detail::ConstVisitorResult<V, Types...>::type folly::DiscriminatedPtr< Types >::apply ( V &&  visitor) const
inline

Definition at line 184 of file DiscriminatedPtr.h.

References folly::DiscriminatedPtr< Types >::index(), and folly::DiscriminatedPtr< Types >::ptr().

185  {
186  size_t n = index();
187  if (n == 0) {
188  throw std::invalid_argument("Empty DiscriminatedPtr");
189  }
190  return dptr_detail::ApplyConstVisitor<V, Types...>()(
191  n, std::forward<V>(visitor), ptr());
192  }
uint16_t index() const
ApplyConstVisitor1< sizeof...(Types), V, typename ConstVisitorResult< V, Types... >::type, Types... > ApplyConstVisitor
template<typename... Types>
void folly::DiscriminatedPtr< Types >::clear ( )
inline

Clear this DiscriminatedPtr, making it empty.

Definition at line 147 of file DiscriminatedPtr.h.

References folly::DiscriminatedPtr< Types >::data_.

147  {
148  data_ = 0;
149  }
template<typename... Types>
bool folly::DiscriminatedPtr< Types >::empty ( ) const
inline

Return true iff this DiscriminatedPtr is empty.

Definition at line 130 of file DiscriminatedPtr.h.

References folly::DiscriminatedPtr< Types >::index().

130  {
131  return index() == 0;
132  }
uint16_t index() const
template<typename... Types>
template<typename T >
T* folly::DiscriminatedPtr< Types >::get ( )
inline

Get a pointer to the object that this DiscriminatedPtr points to, if it is of type T. Fails at compile time if T is not a valid type (listed in Types), and throws std::invalid_argument if this DiscriminatedPtr is empty or points to an object of a different type.

Definition at line 112 of file DiscriminatedPtr.h.

References folly::DiscriminatedPtr< Types >::ptr(), folly::T, and UNLIKELY.

112  {
113  if (UNLIKELY(!hasType<T>())) {
114  throw std::invalid_argument("Invalid type");
115  }
116  return static_cast<T*>(ptr());
117  }
folly::std T
#define UNLIKELY(x)
Definition: Likely.h:48
template<typename... Types>
template<typename T >
const T* folly::DiscriminatedPtr< Types >::get ( ) const
inline

Definition at line 120 of file DiscriminatedPtr.h.

References folly::DiscriminatedPtr< Types >::ptr(), folly::T, and UNLIKELY.

120  {
121  if (UNLIKELY(!hasType<T>())) {
122  throw std::invalid_argument("Invalid type");
123  }
124  return static_cast<const T*>(ptr());
125  }
folly::std T
#define UNLIKELY(x)
Definition: Likely.h:48
template<typename... Types>
template<typename T >
T* folly::DiscriminatedPtr< Types >::get_nothrow ( )
inlinenoexcept

Get a pointer to the object that this DiscriminatedPtr points to, if it is of type T. Fails at compile time if T is not a valid type (listed in Types), and returns nullptr if this DiscriminatedPtr is empty or points to an object of a different type.

Definition at line 94 of file DiscriminatedPtr.h.

References LIKELY, folly::DiscriminatedPtr< Types >::ptr(), and folly::T.

94  {
95  void* p = LIKELY(hasType<T>()) ? ptr() : nullptr;
96  return static_cast<T*>(p);
97  }
#define LIKELY(x)
Definition: Likely.h:47
folly::std T
#define nullptr
Definition: http_parser.c:41
template<typename... Types>
template<typename T >
const T* folly::DiscriminatedPtr< Types >::get_nothrow ( ) const
inlinenoexcept

Definition at line 100 of file DiscriminatedPtr.h.

References LIKELY, folly::DiscriminatedPtr< Types >::ptr(), and folly::T.

100  {
101  const void* p = LIKELY(hasType<T>()) ? ptr() : nullptr;
102  return static_cast<const T*>(p);
103  }
#define LIKELY(x)
Definition: Likely.h:47
folly::std T
#define nullptr
Definition: http_parser.c:41
template<typename... Types>
template<typename T >
bool folly::DiscriminatedPtr< Types >::hasType ( ) const
inline

Return true iff the object pointed by this DiscriminatedPtr has type T, false otherwise. Fails at compile time if T is not a valid type (listed in Types...)

Definition at line 140 of file DiscriminatedPtr.h.

References folly::DiscriminatedPtr< Types >::index().

140  {
141  return index() == typeIndex<T>();
142  }
uint16_t index() const
template<typename... Types>
uint16_t folly::DiscriminatedPtr< Types >::index ( ) const
inlineprivate
template<typename... Types>
template<typename T >
DiscriminatedPtr& folly::DiscriminatedPtr< Types >::operator= ( T ptr)
inline

Assignment operator from a pointer of type T.

Definition at line 155 of file DiscriminatedPtr.h.

References folly::DiscriminatedPtr< Types >::ptr().

155  {
156  set(ptr);
157  return *this;
158  }
template<typename... Types>
template<typename T >
void folly::DiscriminatedPtr< Types >::set ( T ptr)
inline

Set this DiscriminatedPtr to point to an object of type T. Fails at compile time if T is not a valid type (listed in Types)

Definition at line 83 of file DiscriminatedPtr.h.

References folly::DiscriminatedPtr< Types >::ptr().

83  {
84  set(ptr, typeIndex<T>());
85  }
template<typename... Types>
void folly::DiscriminatedPtr< Types >::set ( void *  p,
uint16_t  v 
)
inlineprivate

Definition at line 210 of file DiscriminatedPtr.h.

References folly::DiscriminatedPtr< Types >::data_, and v.

210  {
211  uintptr_t ip = reinterpret_cast<uintptr_t>(p);
212  CHECK(!(ip >> 48));
213  ip |= static_cast<uintptr_t>(v) << 48;
214  data_ = ip;
215  }
auto v
template<typename... Types>
template<typename T >
uint16_t folly::DiscriminatedPtr< Types >::typeIndex ( ) const
inlineprivate

Get the 1-based type index of T in Types.

Definition at line 199 of file DiscriminatedPtr.h.

References uint16_t.

199  {
201  }
static const char *const value
Definition: Conv.cpp:50

Member Data Documentation

template<typename... Types>
uintptr_t folly::DiscriminatedPtr< Types >::data_
private

We store a pointer in the least significant 48 bits of data_, and a type index (0 = empty, or 1-based index in Types) in the most significant 16 bits. We rely on the fact that pointers have their most significant 16 bits clear on x86_64.

Definition at line 223 of file DiscriminatedPtr.h.

Referenced by folly::DiscriminatedPtr< Types >::clear(), folly::DiscriminatedPtr< Types >::index(), folly::DiscriminatedPtr< Types >::ptr(), and folly::DiscriminatedPtr< Types >::set().


The documentation for this class was generated from the following file: