#pragma once #include "dxxsconf.h" #include "compiler-type_traits.h" template class exact_type { T *p; public: operator bool() const = delete; // Conversion to void* variants is prohibited operator void *() const = delete; operator volatile void *() const = delete; operator const void *() const = delete; operator const volatile void *() const = delete; bool operator<(exact_type) const = delete; bool operator<=(exact_type) const = delete; bool operator>(exact_type) const = delete; bool operator>=(exact_type) const = delete; exact_type(T *t) : p(t) {} // Conversion to the exact type is permitted operator T *() const { return p; } bool operator==(exact_type rhs) const { return p == rhs.p; } bool operator!=(exact_type rhs) const { return p != rhs.p; } }; template class prohibit_void_ptr { public: // Return a proxy when the address is taken exact_type operator&() { return static_cast(this); } exact_type operator&() const { return static_cast(this); } }; struct allow_void_ptr {}; template struct has_prohibit_void_ptr : tt::is_base_of, T> {}; template struct has_prohibit_void_ptr {}; template struct inherit_void_ptr_handler : public tt::conditional::value, prohibit_void_ptr, allow_void_ptr> {};