18 #ifndef STATIC_ASSERT_H
23 #define SAFE_DOWNCASTS
41 template <
typename B,
typename D>
47 template <
typename B,
typename D>
49 typedef const volatile B
CVB;
50 typedef const volatile D CVD;
52 template <
typename T>
static yes check(CVD*,
T);
58 template <
typename T,
typename U>
69 static const bool value = (
sizeof(
check1(t, u)) ==
sizeof(
yes)) && (
sizeof(
check2(t, u)) ==
sizeof(
yes));
95 #if defined(SAFE_DOWNCASTS)
97 template<
class DERIVED>
98 inline DERIVED assert_downcasted(DERIVED expr) {
103 template<
class DERIVED,
class BASE>
104 inline DERIVED *safe_pointer_downcast(BASE *expr) {
115 ? assert_downcasted<DERIVED*>(
dynamic_cast<DERIVED*
>(expr))
119 template<
class DERIVED_PTR,
class BASE_PTR>
120 inline DERIVED_PTR safe_downcast(BASE_PTR expr) {
127 return safe_pointer_downcast<DERIVED,BASE>(expr);
130 #define DOWNCAST(totype,expr) safe_downcast<totype,typeof(expr)>(expr)
134 template<
class DERIVED_PTR,
class BASE_PTR>
138 return static_cast<DERIVED_PTR
>(expr);
141 #define DOWNCAST(totype,expr) static_downcast<totype,typeof(expr)>(expr) // fixes undefined behavior
143 #endif // SAFE_DOWNCASTS
147 #define DEFINE_DOWNCAST_ACCESSORS(CLASS, NAME, VALUE) \
148 CLASS *NAME() { return DOWNCAST(CLASS*, VALUE); } \
149 const CLASS *NAME() const { return DOWNCAST(const CLASS*, VALUE); }
152 #define DOWNCAST_REFERENCE(totype,expr) (*DOWNCAST(totype*, &(expr)))
155 #error downcast.h included twice
static const bool possible
#define STATIC_ASSERT_ANNOTATED(const_expression, annotation)
static yes check1(T *, T *)
remove_volatile< typename remove_const< T >::type >::type type
DERIVED_PTR static_downcast(BASE_PTR expr)
static yes check2(U *, U *)
static yes check(CVD *, T)