--- gvpe/src/callback.h 2007/12/02 00:54:52 1.11 +++ gvpe/src/callback.h 2007/12/04 15:01:12 1.12 @@ -28,37 +28,50 @@ #define CALLBACK_H_VERSION 3 -template -struct callback_funtype_trait; +template +struct callback; -template -struct callback_get_impl; +#define callback_set(callback,obj,klass,method) callback.set (obj) template -class callback0 +struct callback { - struct klass; // it is vital that this is never defined + typedef R (*ptr_type)(void *self); - typedef R (klass::*ptr_type)(); +private: - klass *o; - R (klass::*m)(); + void *self; + ptr_type func; + +protected: + + template + struct thunktype; + + template + struct thunktype + { + typedef klass K; + }; + + template + static R thunk (void *self) + { + klass *obj = static_cast(self); + return (obj->*method) (); + } public: - template - explicit callback0 (O1 *object, R (O2::*method)()) + template + void set (K *object) { - o = reinterpret_cast(object); - m = reinterpret_cast(method); + self = object; + func = thunk; } - // this works because a standards-compliant C++ compiler - // basically can't help it: it doesn't have the knowledge - // required to miscompile (klass is not defined anywhere - // and nothing is known about the constructor arguments) :) - R call() const + R call () const { - return (o->*m) (); + return func (self); } R operator ()() const @@ -67,52 +80,45 @@ } }; -template -struct callback_funtype_trait0 +template +struct callback { - static const int arity = 0; - typedef R type (void); - typedef R result_type; - -}; + typedef R (*ptr_type)(void *self, A1); -template -struct callback_funtype_trait : callback_funtype_trait0 -{ -}; +private: -template -struct callback_get_impl<0, signature> -{ - typedef callback_funtype_trait T; - typedef callback0 type; -}; - -template -class callback1 -{ - struct klass; // it is vital that this is never defined + void *self; + ptr_type func; - typedef R (klass::*ptr_type)(A1); +protected: - klass *o; - R (klass::*m)(A1); + template + struct thunktype; + + template + struct thunktype + { + typedef klass K; + }; + + template + static R thunk (void *self, A1 a1) + { + klass *obj = static_cast(self); + return (obj->*method) (a1); + } public: - template - explicit callback1 (O1 *object, R (O2::*method)(A1)) + template + void set (K *object) { - o = reinterpret_cast(object); - m = reinterpret_cast(method); + self = object; + func = thunk; } - // this works because a standards-compliant C++ compiler - // basically can't help it: it doesn't have the knowledge - // required to miscompile (klass is not defined anywhere - // and nothing is known about the constructor arguments) :) - R call(A1 a1) const + R call (A1 a1) const { - return (o->*m) (a1); + return func (self, a1); } R operator ()(A1 a1) const @@ -121,52 +127,45 @@ } }; -template -struct callback_funtype_trait1 +template +struct callback { - static const int arity = 1; - typedef R type (A1); - typedef R result_type; - typedef A1 arg1_type; -}; + typedef R (*ptr_type)(void *self, A1, A2); -template -struct callback_funtype_trait : callback_funtype_trait1 -{ -}; +private: -template -struct callback_get_impl<1, signature> -{ - typedef callback_funtype_trait T; - typedef callback1 type; -}; - -template -class callback2 -{ - struct klass; // it is vital that this is never defined + void *self; + ptr_type func; + +protected: - typedef R (klass::*ptr_type)(A1, A2); + template + struct thunktype; - klass *o; - R (klass::*m)(A1, A2); + template + struct thunktype + { + typedef klass K; + }; + + template + static R thunk (void *self, A1 a1, A2 a2) + { + klass *obj = static_cast(self); + return (obj->*method) (a1, a2); + } public: - template - explicit callback2 (O1 *object, R (O2::*method)(A1, A2)) + template + void set (K *object) { - o = reinterpret_cast(object); - m = reinterpret_cast(method); + self = object; + func = thunk; } - // this works because a standards-compliant C++ compiler - // basically can't help it: it doesn't have the knowledge - // required to miscompile (klass is not defined anywhere - // and nothing is known about the constructor arguments) :) - R call(A1 a1, A2 a2) const + R call (A1 a1, A2 a2) const { - return (o->*m) (a1, a2); + return func (self, a1, a2); } R operator ()(A1 a1, A2 a2) const @@ -175,52 +174,45 @@ } }; -template -struct callback_funtype_trait2 +template +struct callback { - static const int arity = 2; - typedef R type (A1, A2); - typedef R result_type; - typedef A1 arg1_type; typedef A2 arg2_type; -}; + typedef R (*ptr_type)(void *self, A1, A2, A3); -template -struct callback_funtype_trait : callback_funtype_trait2 -{ -}; +private: -template -struct callback_get_impl<2, signature> -{ - typedef callback_funtype_trait T; - typedef callback2 type; -}; - -template -class callback3 -{ - struct klass; // it is vital that this is never defined + void *self; + ptr_type func; - typedef R (klass::*ptr_type)(A1, A2, A3); +protected: - klass *o; - R (klass::*m)(A1, A2, A3); + template + struct thunktype; + + template + struct thunktype + { + typedef klass K; + }; + + template + static R thunk (void *self, A1 a1, A2 a2, A3 a3) + { + klass *obj = static_cast(self); + return (obj->*method) (a1, a2, a3); + } public: - template - explicit callback3 (O1 *object, R (O2::*method)(A1, A2, A3)) + template + void set (K *object) { - o = reinterpret_cast(object); - m = reinterpret_cast(method); + self = object; + func = thunk; } - // this works because a standards-compliant C++ compiler - // basically can't help it: it doesn't have the knowledge - // required to miscompile (klass is not defined anywhere - // and nothing is known about the constructor arguments) :) - R call(A1 a1, A2 a2, A3 a3) const + R call (A1 a1, A2 a2, A3 a3) const { - return (o->*m) (a1, a2, a3); + return func (self, a1, a2, a3); } R operator ()(A1 a1, A2 a2, A3 a3) const @@ -229,52 +221,45 @@ } }; -template -struct callback_funtype_trait3 +template +struct callback { - static const int arity = 3; - typedef R type (A1, A2, A3); - typedef R result_type; - typedef A1 arg1_type; typedef A2 arg2_type; typedef A3 arg3_type; -}; + typedef R (*ptr_type)(void *self, A1, A2, A3, A4); -template -struct callback_funtype_trait : callback_funtype_trait3 -{ -}; +private: -template -struct callback_get_impl<3, signature> -{ - typedef callback_funtype_trait T; - typedef callback3 type; -}; - -template -class callback4 -{ - struct klass; // it is vital that this is never defined + void *self; + ptr_type func; + +protected: - typedef R (klass::*ptr_type)(A1, A2, A3, A4); + template + struct thunktype; - klass *o; - R (klass::*m)(A1, A2, A3, A4); + template + struct thunktype + { + typedef klass K; + }; + + template + static R thunk (void *self, A1 a1, A2 a2, A3 a3, A4 a4) + { + klass *obj = static_cast(self); + return (obj->*method) (a1, a2, a3, a4); + } public: - template - explicit callback4 (O1 *object, R (O2::*method)(A1, A2, A3, A4)) + template + void set (K *object) { - o = reinterpret_cast(object); - m = reinterpret_cast(method); + self = object; + func = thunk; } - // this works because a standards-compliant C++ compiler - // basically can't help it: it doesn't have the knowledge - // required to miscompile (klass is not defined anywhere - // and nothing is known about the constructor arguments) :) - R call(A1 a1, A2 a2, A3 a3, A4 a4) const + R call (A1 a1, A2 a2, A3 a3, A4 a4) const { - return (o->*m) (a1, a2, a3, a4); + return func (self, a1, a2, a3, a4); } R operator ()(A1 a1, A2 a2, A3 a3, A4 a4) const @@ -283,52 +268,45 @@ } }; -template -struct callback_funtype_trait4 +template +struct callback { - static const int arity = 4; - typedef R type (A1, A2, A3, A4); - typedef R result_type; - typedef A1 arg1_type; typedef A2 arg2_type; typedef A3 arg3_type; typedef A4 arg4_type; -}; + typedef R (*ptr_type)(void *self, A1, A2, A3, A4, A5); -template -struct callback_funtype_trait : callback_funtype_trait4 -{ -}; +private: -template -struct callback_get_impl<4, signature> -{ - typedef callback_funtype_trait T; - typedef callback4 type; -}; - -template -class callback5 -{ - struct klass; // it is vital that this is never defined + void *self; + ptr_type func; - typedef R (klass::*ptr_type)(A1, A2, A3, A4, A5); +protected: - klass *o; - R (klass::*m)(A1, A2, A3, A4, A5); + template + struct thunktype; + + template + struct thunktype + { + typedef klass K; + }; + + template + static R thunk (void *self, A1 a1, A2 a2, A3 a3, A4 a4, A5 a5) + { + klass *obj = static_cast(self); + return (obj->*method) (a1, a2, a3, a4, a5); + } public: - template - explicit callback5 (O1 *object, R (O2::*method)(A1, A2, A3, A4, A5)) + template + void set (K *object) { - o = reinterpret_cast(object); - m = reinterpret_cast(method); + self = object; + func = thunk; } - // this works because a standards-compliant C++ compiler - // basically can't help it: it doesn't have the knowledge - // required to miscompile (klass is not defined anywhere - // and nothing is known about the constructor arguments) :) - R call(A1 a1, A2 a2, A3 a3, A4 a4, A5 a5) const + R call (A1 a1, A2 a2, A3 a3, A4 a4, A5 a5) const { - return (o->*m) (a1, a2, a3, a4, a5); + return func (self, a1, a2, a3, a4, a5); } R operator ()(A1 a1, A2 a2, A3 a3, A4 a4, A5 a5) const @@ -337,52 +315,45 @@ } }; -template -struct callback_funtype_trait5 +template +struct callback { - static const int arity = 5; - typedef R type (A1, A2, A3, A4, A5); - typedef R result_type; - typedef A1 arg1_type; typedef A2 arg2_type; typedef A3 arg3_type; typedef A4 arg4_type; typedef A5 arg5_type; -}; + typedef R (*ptr_type)(void *self, A1, A2, A3, A4, A5, A6); -template -struct callback_funtype_trait : callback_funtype_trait5 -{ -}; +private: -template -struct callback_get_impl<5, signature> -{ - typedef callback_funtype_trait T; - typedef callback5 type; -}; - -template -class callback6 -{ - struct klass; // it is vital that this is never defined + void *self; + ptr_type func; - typedef R (klass::*ptr_type)(A1, A2, A3, A4, A5, A6); +protected: - klass *o; - R (klass::*m)(A1, A2, A3, A4, A5, A6); + template + struct thunktype; + + template + struct thunktype + { + typedef klass K; + }; + + template + static R thunk (void *self, A1 a1, A2 a2, A3 a3, A4 a4, A5 a5, A6 a6) + { + klass *obj = static_cast(self); + return (obj->*method) (a1, a2, a3, a4, a5, a6); + } public: - template - explicit callback6 (O1 *object, R (O2::*method)(A1, A2, A3, A4, A5, A6)) + template + void set (K *object) { - o = reinterpret_cast(object); - m = reinterpret_cast(method); + self = object; + func = thunk; } - // this works because a standards-compliant C++ compiler - // basically can't help it: it doesn't have the knowledge - // required to miscompile (klass is not defined anywhere - // and nothing is known about the constructor arguments) :) - R call(A1 a1, A2 a2, A3 a3, A4 a4, A5 a5, A6 a6) const + R call (A1 a1, A2 a2, A3 a3, A4 a4, A5 a5, A6 a6) const { - return (o->*m) (a1, a2, a3, a4, a5, a6); + return func (self, a1, a2, a3, a4, a5, a6); } R operator ()(A1 a1, A2 a2, A3 a3, A4 a4, A5 a5, A6 a6) const @@ -391,52 +362,45 @@ } }; -template -struct callback_funtype_trait6 +template +struct callback { - static const int arity = 6; - typedef R type (A1, A2, A3, A4, A5, A6); - typedef R result_type; - typedef A1 arg1_type; typedef A2 arg2_type; typedef A3 arg3_type; typedef A4 arg4_type; typedef A5 arg5_type; typedef A6 arg6_type; -}; + typedef R (*ptr_type)(void *self, A1, A2, A3, A4, A5, A6, A7); -template -struct callback_funtype_trait : callback_funtype_trait6 -{ -}; +private: -template -struct callback_get_impl<6, signature> -{ - typedef callback_funtype_trait T; - typedef callback6 type; -}; - -template -class callback7 -{ - struct klass; // it is vital that this is never defined + void *self; + ptr_type func; - typedef R (klass::*ptr_type)(A1, A2, A3, A4, A5, A6, A7); +protected: - klass *o; - R (klass::*m)(A1, A2, A3, A4, A5, A6, A7); + template + struct thunktype; + + template + struct thunktype + { + typedef klass K; + }; + + template + static R thunk (void *self, A1 a1, A2 a2, A3 a3, A4 a4, A5 a5, A6 a6, A7 a7) + { + klass *obj = static_cast(self); + return (obj->*method) (a1, a2, a3, a4, a5, a6, a7); + } public: - template - explicit callback7 (O1 *object, R (O2::*method)(A1, A2, A3, A4, A5, A6, A7)) + template + void set (K *object) { - o = reinterpret_cast(object); - m = reinterpret_cast(method); + self = object; + func = thunk; } - // this works because a standards-compliant C++ compiler - // basically can't help it: it doesn't have the knowledge - // required to miscompile (klass is not defined anywhere - // and nothing is known about the constructor arguments) :) - R call(A1 a1, A2 a2, A3 a3, A4 a4, A5 a5, A6 a6, A7 a7) const + R call (A1 a1, A2 a2, A3 a3, A4 a4, A5 a5, A6 a6, A7 a7) const { - return (o->*m) (a1, a2, a3, a4, a5, a6, a7); + return func (self, a1, a2, a3, a4, a5, a6, a7); } R operator ()(A1 a1, A2 a2, A3 a3, A4 a4, A5 a5, A6 a6, A7 a7) const @@ -445,52 +409,45 @@ } }; -template -struct callback_funtype_trait7 +template +struct callback { - static const int arity = 7; - typedef R type (A1, A2, A3, A4, A5, A6, A7); - typedef R result_type; - typedef A1 arg1_type; typedef A2 arg2_type; typedef A3 arg3_type; typedef A4 arg4_type; typedef A5 arg5_type; typedef A6 arg6_type; typedef A7 arg7_type; -}; + typedef R (*ptr_type)(void *self, A1, A2, A3, A4, A5, A6, A7, A8); -template -struct callback_funtype_trait : callback_funtype_trait7 -{ -}; +private: -template -struct callback_get_impl<7, signature> -{ - typedef callback_funtype_trait T; - typedef callback7 type; -}; - -template -class callback8 -{ - struct klass; // it is vital that this is never defined + void *self; + ptr_type func; + +protected: - typedef R (klass::*ptr_type)(A1, A2, A3, A4, A5, A6, A7, A8); + template + struct thunktype; + + template + struct thunktype + { + typedef klass K; + }; - klass *o; - R (klass::*m)(A1, A2, A3, A4, A5, A6, A7, A8); + template + static R thunk (void *self, A1 a1, A2 a2, A3 a3, A4 a4, A5 a5, A6 a6, A7 a7, A8 a8) + { + klass *obj = static_cast(self); + return (obj->*method) (a1, a2, a3, a4, a5, a6, a7, a8); + } public: - template - explicit callback8 (O1 *object, R (O2::*method)(A1, A2, A3, A4, A5, A6, A7, A8)) + template + void set (K *object) { - o = reinterpret_cast(object); - m = reinterpret_cast(method); + self = object; + func = thunk; } - // this works because a standards-compliant C++ compiler - // basically can't help it: it doesn't have the knowledge - // required to miscompile (klass is not defined anywhere - // and nothing is known about the constructor arguments) :) - R call(A1 a1, A2 a2, A3 a3, A4 a4, A5 a5, A6 a6, A7 a7, A8 a8) const + R call (A1 a1, A2 a2, A3 a3, A4 a4, A5 a5, A6 a6, A7 a7, A8 a8) const { - return (o->*m) (a1, a2, a3, a4, a5, a6, a7, a8); + return func (self, a1, a2, a3, a4, a5, a6, a7, a8); } R operator ()(A1 a1, A2 a2, A3 a3, A4 a4, A5 a5, A6 a6, A7 a7, A8 a8) const @@ -499,52 +456,45 @@ } }; -template -struct callback_funtype_trait8 +template +struct callback { - static const int arity = 8; - typedef R type (A1, A2, A3, A4, A5, A6, A7, A8); - typedef R result_type; - typedef A1 arg1_type; typedef A2 arg2_type; typedef A3 arg3_type; typedef A4 arg4_type; typedef A5 arg5_type; typedef A6 arg6_type; typedef A7 arg7_type; typedef A8 arg8_type; -}; + typedef R (*ptr_type)(void *self, A1, A2, A3, A4, A5, A6, A7, A8, A9); -template -struct callback_funtype_trait : callback_funtype_trait8 -{ -}; +private: -template -struct callback_get_impl<8, signature> -{ - typedef callback_funtype_trait T; - typedef callback8 type; -}; - -template -class callback9 -{ - struct klass; // it is vital that this is never defined + void *self; + ptr_type func; + +protected: - typedef R (klass::*ptr_type)(A1, A2, A3, A4, A5, A6, A7, A8, A9); + template + struct thunktype; - klass *o; - R (klass::*m)(A1, A2, A3, A4, A5, A6, A7, A8, A9); + template + struct thunktype + { + typedef klass K; + }; + + template + static R thunk (void *self, A1 a1, A2 a2, A3 a3, A4 a4, A5 a5, A6 a6, A7 a7, A8 a8, A9 a9) + { + klass *obj = static_cast(self); + return (obj->*method) (a1, a2, a3, a4, a5, a6, a7, a8, a9); + } public: - template - explicit callback9 (O1 *object, R (O2::*method)(A1, A2, A3, A4, A5, A6, A7, A8, A9)) + template + void set (K *object) { - o = reinterpret_cast(object); - m = reinterpret_cast(method); + self = object; + func = thunk; } - // this works because a standards-compliant C++ compiler - // basically can't help it: it doesn't have the knowledge - // required to miscompile (klass is not defined anywhere - // and nothing is known about the constructor arguments) :) - R call(A1 a1, A2 a2, A3 a3, A4 a4, A5 a5, A6 a6, A7 a7, A8 a8, A9 a9) const + R call (A1 a1, A2 a2, A3 a3, A4 a4, A5 a5, A6 a6, A7 a7, A8 a8, A9 a9) const { - return (o->*m) (a1, a2, a3, a4, a5, a6, a7, a8, a9); + return func (self, a1, a2, a3, a4, a5, a6, a7, a8, a9); } R operator ()(A1 a1, A2 a2, A3 a3, A4 a4, A5 a5, A6 a6, A7 a7, A8 a8, A9 a9) const @@ -553,52 +503,45 @@ } }; -template -struct callback_funtype_trait9 +template +struct callback { - static const int arity = 9; - typedef R type (A1, A2, A3, A4, A5, A6, A7, A8, A9); - typedef R result_type; - typedef A1 arg1_type; typedef A2 arg2_type; typedef A3 arg3_type; typedef A4 arg4_type; typedef A5 arg5_type; typedef A6 arg6_type; typedef A7 arg7_type; typedef A8 arg8_type; typedef A9 arg9_type; -}; + typedef R (*ptr_type)(void *self, A1, A2, A3, A4, A5, A6, A7, A8, A9, A10); -template -struct callback_funtype_trait : callback_funtype_trait9 -{ -}; +private: -template -struct callback_get_impl<9, signature> -{ - typedef callback_funtype_trait T; - typedef callback9 type; -}; - -template -class callback10 -{ - struct klass; // it is vital that this is never defined + void *self; + ptr_type func; - typedef R (klass::*ptr_type)(A1, A2, A3, A4, A5, A6, A7, A8, A9, A10); +protected: - klass *o; - R (klass::*m)(A1, A2, A3, A4, A5, A6, A7, A8, A9, A10); + template + struct thunktype; + + template + struct thunktype + { + typedef klass K; + }; + + template + static R thunk (void *self, A1 a1, A2 a2, A3 a3, A4 a4, A5 a5, A6 a6, A7 a7, A8 a8, A9 a9, A10 a10) + { + klass *obj = static_cast(self); + return (obj->*method) (a1, a2, a3, a4, a5, a6, a7, a8, a9, a10); + } public: - template - explicit callback10 (O1 *object, R (O2::*method)(A1, A2, A3, A4, A5, A6, A7, A8, A9, A10)) + template + void set (K *object) { - o = reinterpret_cast(object); - m = reinterpret_cast(method); + self = object; + func = thunk; } - // this works because a standards-compliant C++ compiler - // basically can't help it: it doesn't have the knowledge - // required to miscompile (klass is not defined anywhere - // and nothing is known about the constructor arguments) :) - R call(A1 a1, A2 a2, A3 a3, A4 a4, A5 a5, A6 a6, A7 a7, A8 a8, A9 a9, A10 a10) const + R call (A1 a1, A2 a2, A3 a3, A4 a4, A5 a5, A6 a6, A7 a7, A8 a8, A9 a9, A10 a10) const { - return (o->*m) (a1, a2, a3, a4, a5, a6, a7, a8, a9, a10); + return func (self, a1, a2, a3, a4, a5, a6, a7, a8, a9, a10); } R operator ()(A1 a1, A2 a2, A3 a3, A4 a4, A5 a5, A6 a6, A7 a7, A8 a8, A9 a9, A10 a10) const @@ -607,38 +550,5 @@ } }; -template -struct callback_funtype_trait10 -{ - static const int arity = 10; - typedef R type (A1, A2, A3, A4, A5, A6, A7, A8, A9, A10); - typedef R result_type; - typedef A1 arg1_type; typedef A2 arg2_type; typedef A3 arg3_type; typedef A4 arg4_type; typedef A5 arg5_type; typedef A6 arg6_type; typedef A7 arg7_type; typedef A8 arg8_type; typedef A9 arg9_type; typedef A10 arg10_type; -}; - -template -struct callback_funtype_trait : callback_funtype_trait10 -{ -}; - -template -struct callback_get_impl<10, signature> -{ - typedef callback_funtype_trait T; - typedef callback10 type; -}; - - -template -struct callback : callback_get_impl::arity, signature>::type -{ - typedef typename callback_get_impl::arity, signature>::type base_type; - - template - explicit callback (O object, M method) - : base_type (object, method) - { - } -}; #endif