#include <functional>
namespace sprawl
{
namespace memory
{
template<size_t size>
class OpaquePtr;
template<typename T>
struct CreateAs{};
}
}
template<size_t size>
class sprawl::memory::OpaquePtr
{
public:
class Deleter
{
public:
virtual void Delete(void*) = 0;
};
template<typename T>
class TypeDeleter : public Deleter
{
public:
virtual void Delete(void* ptr)
{
reinterpret_cast<T*>(ptr)->~T();
}
};
template<typename T, typename... Params>
OpaquePtr(CreateAs<T> const&, Params&&... params)
: m_ptr()
, m_deleter() // Same size since no members, direct reinterpret cast should be fine.
{
static_assert(sizeof(T) == size, "Opaque pointer delcared with size that does not match the type used to construct it.");
new(m_ptr) T(std::forward<Params>(params)...);
new(m_deleter) TypeDeleter<T>();
}
~OpaquePtr()
{
reinterpret_cast<Deleter*>(m_deleter)->Delete(m_ptr);
}
template<typename T>
T& As()
{
static_assert(sizeof(T) == size, "Opaque pointer delcared with size that does not match the type used to access it.");
return *reinterpret_cast<T*>(m_ptr);
}
template<typename T>
T const& As() const
{
static_assert(sizeof(T) == size, "Opaque pointer delcared with size that does not match the type used to access it.");
return *reinterpret_cast<T*>(m_ptr);
}
template<typename T>
operator T&()
{
static_assert(sizeof(T) == size, "Opaque pointer delcared with size that does not match the type used to access it.");
return *reinterpret_cast<T*>(m_ptr);
}
template<typename T>
operator T const&() const
{
static_assert(sizeof(T) == size, "Opaque pointer delcared with size that does not match the type used to access it.");
return *reinterpret_cast<T*>(m_ptr);
}
private:
unsigned char m_ptr[size];
unsigned char m_deleter[sizeof(Deleter)];
}; | # | Change | User | Description | Committed | |
|---|---|---|---|---|---|
| #2 | 16225 | ShadauxCat |
- Renamed OpaquePtr to OpaqueType, which is more correct as it isn't a pointer. - Added alignment restriction to OpaqueType - Changed Mutex implementation on Windows to use faster SRWLOCK instead of CRITICAL_SECTION (cannot mirror this change on Linux because pthread_cond_wait can't accept a pthread_rwlock_t) #review-16226 |
||
| #1 | 16223 | ShadauxCat |
Added opaque pointer. Maybe this should really be called OpaqueData, since it's not really a pointer. #review-16224 |