--- gvpe/src/callback.h 2006/01/14 11:21:12 1.9 +++ gvpe/src/callback.h 2007/12/04 17:17:19 1.13 @@ -4,7 +4,7 @@ /* callback.h -- C++ callback mechanism - Copyright (C) 2003-2006 Marc Lehmann + Copyright (C) 2003-2007 Marc Lehmann This file is part of GVPE. @@ -26,348 +26,527 @@ #ifndef CALLBACK_H__ #define CALLBACK_H__ +#define CALLBACK_H_VERSION 3 + +template +struct callback; + template -class callback0 { - struct object { }; +struct callback +{ + typedef R (*ptr_type)(void *self); + +private: + + void *self; + ptr_type func; + +protected: + + template + struct thunktype; - void *obj; - R (object::*meth)(); + template + struct thunktype + { + typedef klass K; + }; + + template + static R thunk (void *self) + { + klass *obj = static_cast(self); + return (obj->*method) (); + } - /* a proxy is a kind of recipe on how to call a specific class method */ - struct proxy_base { - virtual R call (void *obj, R (object::*meth)()) const = 0; - }; - template - struct proxy : proxy_base { - virtual R call (void *obj, R (object::*meth)()) const - { - return (R)((reinterpret_cast(obj)) ->* (reinterpret_cast(meth))) - (); - } - }; - - proxy_base *prxy; - -public: - template - explicit callback0 (O1 *object, R (O2::*method)()) - { - static proxy p; - obj = reinterpret_cast(object); - meth = reinterpret_cast(method); - prxy = &p; - } - - R call() const - { - return prxy->call (obj, meth); - } +public: + template + void set (K *object) + { + self = object; + func = thunk; + } + + R call () const + { + return func (self); + } R operator ()() const - { - return call (); - } + { + return call (); + } }; template -class callback1 { - struct object { }; +struct callback +{ + typedef R (*ptr_type)(void *self, A1); - void *obj; - R (object::*meth)(A1); +private: - /* a proxy is a kind of recipe on how to call a specific class method */ - struct proxy_base { - virtual R call (void *obj, R (object::*meth)(A1), A1 a1) const = 0; - }; - template - struct proxy : proxy_base { - virtual R call (void *obj, R (object::*meth)(A1), A1 a1) const - { - return (R)((reinterpret_cast(obj)) ->* (reinterpret_cast(meth))) - (a1); - } - }; - - proxy_base *prxy; - -public: - template - explicit callback1 (O1 *object, R (O2::*method)(A1)) - { - static proxy p; - obj = reinterpret_cast(object); - meth = reinterpret_cast(method); - prxy = &p; - } - - R call(A1 a1) const - { - return prxy->call (obj, meth, a1); - } + void *self; + ptr_type func; + +protected: + + 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 + void set (K *object) + { + self = object; + func = thunk; + } + + R call (A1 a1) const + { + return func (self, a1); + } R operator ()(A1 a1) const - { - return call (a1); - } + { + return call (a1); + } }; template -class callback2 { - struct object { }; +struct callback +{ + typedef R (*ptr_type)(void *self, A1, A2); + +private: + + void *self; + ptr_type func; - void *obj; - R (object::*meth)(A1, A2); +protected: - /* a proxy is a kind of recipe on how to call a specific class method */ - struct proxy_base { - virtual R call (void *obj, R (object::*meth)(A1, A2), A1 a1, A2 a2) const = 0; - }; - template - struct proxy : proxy_base { - virtual R call (void *obj, R (object::*meth)(A1, A2), A1 a1, A2 a2) const - { - return (R)((reinterpret_cast(obj)) ->* (reinterpret_cast(meth))) - (a1, a2); - } - }; - - proxy_base *prxy; - -public: - template - explicit callback2 (O1 *object, R (O2::*method)(A1, A2)) - { - static proxy p; - obj = reinterpret_cast(object); - meth = reinterpret_cast(method); - prxy = &p; - } - - R call(A1 a1, A2 a2) const - { - return prxy->call (obj, meth, a1, a2); - } + template + struct thunktype; + + 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 + void set (K *object) + { + self = object; + func = thunk; + } + + R call (A1 a1, A2 a2) const + { + return func (self, a1, a2); + } R operator ()(A1 a1, A2 a2) const - { - return call (a1, a2); - } + { + return call (a1, a2); + } }; template -class callback3 { - struct object { }; +struct callback +{ + typedef R (*ptr_type)(void *self, A1, A2, A3); - void *obj; - R (object::*meth)(A1, A2, A3); +private: - /* a proxy is a kind of recipe on how to call a specific class method */ - struct proxy_base { - virtual R call (void *obj, R (object::*meth)(A1, A2, A3), A1 a1, A2 a2, A3 a3) const = 0; - }; - template - struct proxy : proxy_base { - virtual R call (void *obj, R (object::*meth)(A1, A2, A3), A1 a1, A2 a2, A3 a3) const - { - return (R)((reinterpret_cast(obj)) ->* (reinterpret_cast(meth))) - (a1, a2, a3); - } - }; - - proxy_base *prxy; - -public: - template - explicit callback3 (O1 *object, R (O2::*method)(A1, A2, A3)) - { - static proxy p; - obj = reinterpret_cast(object); - meth = reinterpret_cast(method); - prxy = &p; - } - - R call(A1 a1, A2 a2, A3 a3) const - { - return prxy->call (obj, meth, a1, a2, a3); - } + void *self; + ptr_type func; + +protected: + + 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 + void set (K *object) + { + self = object; + func = thunk; + } + + R call (A1 a1, A2 a2, A3 a3) const + { + return func (self, a1, a2, a3); + } R operator ()(A1 a1, A2 a2, A3 a3) const - { - return call (a1, a2, a3); - } + { + return call (a1, a2, a3); + } }; template -class callback4 { - struct object { }; +struct callback +{ + typedef R (*ptr_type)(void *self, A1, A2, A3, A4); + +private: + + void *self; + ptr_type func; - void *obj; - R (object::*meth)(A1, A2, A3, A4); +protected: + + template + struct thunktype; + + template + struct thunktype + { + typedef klass K; + }; - /* a proxy is a kind of recipe on how to call a specific class method */ - struct proxy_base { - virtual R call (void *obj, R (object::*meth)(A1, A2, A3, A4), A1 a1, A2 a2, A3 a3, A4 a4) const = 0; - }; - template - struct proxy : proxy_base { - virtual R call (void *obj, R (object::*meth)(A1, A2, A3, A4), A1 a1, A2 a2, A3 a3, A4 a4) const - { - return (R)((reinterpret_cast(obj)) ->* (reinterpret_cast(meth))) - (a1, a2, a3, a4); - } - }; - - proxy_base *prxy; - -public: - template - explicit callback4 (O1 *object, R (O2::*method)(A1, A2, A3, A4)) - { - static proxy p; - obj = reinterpret_cast(object); - meth = reinterpret_cast(method); - prxy = &p; - } - - R call(A1 a1, A2 a2, A3 a3, A4 a4) const - { - return prxy->call (obj, meth, a1, a2, a3, a4); - } + 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 + void set (K *object) + { + self = object; + func = thunk; + } + + R call (A1 a1, A2 a2, A3 a3, A4 a4) const + { + return func (self, a1, a2, a3, a4); + } R operator ()(A1 a1, A2 a2, A3 a3, A4 a4) const - { - return call (a1, a2, a3, a4); - } + { + return call (a1, a2, a3, a4); + } }; template -class callback5 { - struct object { }; +struct callback +{ + typedef R (*ptr_type)(void *self, A1, A2, A3, A4, A5); + +private: - void *obj; - R (object::*meth)(A1, A2, A3, A4, A5); + void *self; + ptr_type func; - /* a proxy is a kind of recipe on how to call a specific class method */ - struct proxy_base { - virtual R call (void *obj, R (object::*meth)(A1, A2, A3, A4, A5), A1 a1, A2 a2, A3 a3, A4 a4, A5 a5) const = 0; - }; - template - struct proxy : proxy_base { - virtual R call (void *obj, R (object::*meth)(A1, A2, A3, A4, A5), A1 a1, A2 a2, A3 a3, A4 a4, A5 a5) const - { - return (R)((reinterpret_cast(obj)) ->* (reinterpret_cast(meth))) - (a1, a2, a3, a4, a5); - } - }; - - proxy_base *prxy; - -public: - template - explicit callback5 (O1 *object, R (O2::*method)(A1, A2, A3, A4, A5)) - { - static proxy p; - obj = reinterpret_cast(object); - meth = reinterpret_cast(method); - prxy = &p; - } - - R call(A1 a1, A2 a2, A3 a3, A4 a4, A5 a5) const - { - return prxy->call (obj, meth, a1, a2, a3, a4, a5); - } +protected: + + 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 + void set (K *object) + { + self = object; + func = thunk; + } + + R call (A1 a1, A2 a2, A3 a3, A4 a4, A5 a5) const + { + return func (self, a1, a2, a3, a4, a5); + } R operator ()(A1 a1, A2 a2, A3 a3, A4 a4, A5 a5) const - { - return call (a1, a2, a3, a4, a5); - } + { + return call (a1, a2, a3, a4, a5); + } }; template -class callback6 { - struct object { }; +struct callback +{ + typedef R (*ptr_type)(void *self, A1, A2, A3, A4, A5, A6); + +private: + + void *self; + ptr_type func; - void *obj; - R (object::*meth)(A1, A2, A3, A4, A5, A6); +protected: - /* a proxy is a kind of recipe on how to call a specific class method */ - struct proxy_base { - virtual R call (void *obj, R (object::*meth)(A1, A2, A3, A4, A5, A6), A1 a1, A2 a2, A3 a3, A4 a4, A5 a5, A6 a6) const = 0; - }; - template - struct proxy : proxy_base { - virtual R call (void *obj, R (object::*meth)(A1, A2, A3, A4, A5, A6), A1 a1, A2 a2, A3 a3, A4 a4, A5 a5, A6 a6) const - { - return (R)((reinterpret_cast(obj)) ->* (reinterpret_cast(meth))) - (a1, a2, a3, a4, a5, a6); - } - }; - - proxy_base *prxy; - -public: - template - explicit callback6 (O1 *object, R (O2::*method)(A1, A2, A3, A4, A5, A6)) - { - static proxy p; - obj = reinterpret_cast(object); - meth = reinterpret_cast(method); - prxy = &p; - } - - R call(A1 a1, A2 a2, A3 a3, A4 a4, A5 a5, A6 a6) const - { - return prxy->call (obj, meth, 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 + void set (K *object) + { + self = object; + func = thunk; + } + + R call (A1 a1, A2 a2, A3 a3, A4 a4, A5 a5, A6 a6) const + { + return func (self, a1, a2, a3, a4, a5, a6); + } R operator ()(A1 a1, A2 a2, A3 a3, A4 a4, A5 a5, A6 a6) const - { - return call (a1, a2, a3, a4, a5, a6); - } + { + return call (a1, a2, a3, a4, a5, a6); + } }; template -class callback7 { - struct object { }; +struct callback +{ + typedef R (*ptr_type)(void *self, A1, A2, A3, A4, A5, A6, A7); + +private: - void *obj; - R (object::*meth)(A1, A2, A3, A4, A5, A6, A7); + void *self; + ptr_type func; - /* a proxy is a kind of recipe on how to call a specific class method */ - struct proxy_base { - virtual R call (void *obj, R (object::*meth)(A1, A2, A3, A4, A5, A6, A7), A1 a1, A2 a2, A3 a3, A4 a4, A5 a5, A6 a6, A7 a7) const = 0; - }; - template - struct proxy : proxy_base { - virtual R call (void *obj, R (object::*meth)(A1, A2, A3, A4, A5, A6, A7), A1 a1, A2 a2, A3 a3, A4 a4, A5 a5, A6 a6, A7 a7) const - { - return (R)((reinterpret_cast(obj)) ->* (reinterpret_cast(meth))) - (a1, a2, a3, a4, a5, a6, a7); - } - }; - - proxy_base *prxy; - -public: - template - explicit callback7 (O1 *object, R (O2::*method)(A1, A2, A3, A4, A5, A6, A7)) - { - static proxy p; - obj = reinterpret_cast(object); - meth = reinterpret_cast(method); - prxy = &p; - } - - R call(A1 a1, A2 a2, A3 a3, A4 a4, A5 a5, A6 a6, A7 a7) const - { - return prxy->call (obj, meth, a1, a2, a3, a4, a5, a6, a7); - } +protected: + + 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 + void set (K *object) + { + self = object; + func = thunk; + } + + R call (A1 a1, A2 a2, A3 a3, A4 a4, A5 a5, A6 a6, A7 a7) const + { + 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 - { - return call (a1, a2, a3, a4, a5, a6, a7); - } + { + return call (a1, a2, a3, a4, a5, a6, a7); + } +}; + +template +struct callback +{ + typedef R (*ptr_type)(void *self, A1, A2, A3, A4, A5, A6, A7, A8); + +private: + + void *self; + ptr_type func; + +protected: + + 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) + { + klass *obj = static_cast(self); + return (obj->*method) (a1, a2, a3, a4, a5, a6, a7, a8); + } + +public: + template + void set (K *object) + { + self = object; + func = thunk; + } + + R call (A1 a1, A2 a2, A3 a3, A4 a4, A5 a5, A6 a6, A7 a7, A8 a8) const + { + 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 + { + return call (a1, a2, a3, a4, a5, a6, a7, a8); + } }; +template +struct callback +{ + typedef R (*ptr_type)(void *self, A1, A2, A3, A4, A5, A6, A7, A8, A9); + +private: + + void *self; + ptr_type func; + +protected: + + 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) + { + klass *obj = static_cast(self); + return (obj->*method) (a1, a2, a3, a4, a5, a6, a7, a8, a9); + } + +public: + template + void set (K *object) + { + self = object; + func = thunk; + } + + R call (A1 a1, A2 a2, A3 a3, A4 a4, A5 a5, A6 a6, A7 a7, A8 a8, A9 a9) const + { + 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 + { + return call (a1, a2, a3, a4, a5, a6, a7, a8, a9); + } +}; + +template +struct callback +{ + typedef R (*ptr_type)(void *self, A1, A2, A3, A4, A5, A6, A7, A8, A9, A10); + +private: + + void *self; + ptr_type func; + +protected: + + 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 + void set (K *object) + { + self = object; + func = thunk; + } + + R call (A1 a1, A2 a2, A3 a3, A4 a4, A5 a5, A6 a6, A7 a7, A8 a8, A9 a9, A10 a10) const + { + 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 + { + return call (a1, a2, a3, a4, a5, a6, a7, a8, a9, a10); + } +}; + + #endif