AtxInterfaces.h

Go to the documentation of this file.
00001 /*****************************************************************
00002 |
00003 |   Atomix - Interfaces
00004 |
00005 |   (c) 2002-2006 Gilles Boccon-Gibod
00006 |   Author: Gilles Boccon-Gibod (bok@bok.net)
00007 |
00008  ****************************************************************/
00013 #ifndef _ATX_INTERFACES_H_
00014 #define _ATX_INTERFACES_H_
00015 
00016 /*----------------------------------------------------------------------
00017 |   includes
00018 +---------------------------------------------------------------------*/
00019 #include "AtxConfig.h"
00020 #include "AtxDefs.h"
00021 #include "AtxTypes.h"
00022 
00023 /*----------------------------------------------------------------------
00024 |   error codes
00025 +---------------------------------------------------------------------*/
00026 #define ATX_ERROR_NO_SUCH_INTERFACE (ATX_ERROR_BASE_INTERFACES - 0)
00027 #define ATX_ERROR_INVALID_INTERFACE (ATX_ERROR_BASE_INTERFACES - 1)
00028 #define ATX_ERROR_NO_SUCH_CLASS     (ATX_ERROR_BASE_INTERFACES - 2)
00029 
00030 /*----------------------------------------------------------------------
00031 |   types
00032 +---------------------------------------------------------------------*/
00039 typedef struct {
00040     unsigned long i0;
00041     unsigned long i1;
00042 } ATX_InterfaceId;
00043 
00044 /*----------------------------------------------------------------------
00045 |   macros
00046 +---------------------------------------------------------------------*/
00047 #ifdef __cplusplus
00048 #define ATX_INTERFACE_ID_TYPE_MOD extern "C" const
00049 #else
00050 #define ATX_INTERFACE_ID_TYPE_MOD extern const
00051 #endif /* __cplusplus */
00052 
00053 #if !defined(ATX_OFFSET_OF)
00054 #define ATX_OFFSET_OF(_member,_type) (ATX_POINTER_TO_LONG(&( ((_type *)0)->_member)))
00055 #endif
00056 
00057 #define ATX_SELF_O(_object, _self_type, _interface_type) \
00058     ( (_self_type *)( ((ATX_Byte*)(_object)) - ATX_OFFSET_OF(_interface_type##_Base, _self_type)) )
00059 
00060 #define ATX_SELF(_self_type, _interface_type) ATX_SELF_O(_self, _self_type, _interface_type)
00061 
00062 #define ATX_SELF_EX_O(_object, _self_type, _base_type, _interface_type)   \
00063 ( (_self_type *)( ((ATX_Byte*)(_object)) -                                \
00064     ATX_OFFSET_OF(_base_type##_Base._interface_type##_Base, _self_type)) )
00065 
00066 #define ATX_SELF_EX(_self_type, _base_type, _interface_type) \
00067     ATX_SELF_EX_O(_self, _self_type, _base_type, _interface_type)
00068 
00069 #define ATX_SELF_M(_member, _self_type, _interface_type) \
00070 ( (_self_type *)( ((ATX_Byte*)(_self)) -                 \
00071     ATX_OFFSET_OF(_member._interface_type##_Base, _self_type)) )
00072 
00073 #define ATX_BASE(_object, _base) (_object)->_base##_Base
00074 
00075 #define ATX_BASE_EX(_object, _parent_base, _base) \
00076     (_object)->_parent_base##_Base._base##_Base
00077 
00078 #define ATX_DECLARE_INTERFACE(_iface)                                   \
00079 ATX_INTERFACE_ID_TYPE_MOD ATX_InterfaceId ATX_INTERFACE_ID__##_iface;   \
00080 typedef struct _iface##Interface _iface##Interface;                     \
00081 typedef struct {                                                        \
00082     const _iface##Interface* iface;                                     \
00083 } _iface;
00084 
00085 #define ATX_BEGIN_INTERFACE_DEFINITION(_iface) struct _iface##Interface { \
00086     ATX_Object* (*GetInterface)(_iface*                instance,          \
00087                                 const ATX_InterfaceId* id);     
00088 #define ATX_END_INTERFACE_DEFINITION };
00089 
00090 #define ATX_BEGIN_INTERFACE_IMPLEMENTATION(_iface,_class)       \
00091 static const _iface##Interface _class##_##_class##Interface = { \
00092     _class##_GetInterface,                                      
00093 #define ATX_END_INTERFACE_IMPLEMENTATION(_iface,_class) };
00094 
00095 #define ATX_IMPLEMENTS(_iface) _iface _iface##_Base
00096 #define ATX_EXTENDS(_class)    _class _class##_Base
00097 
00101 #define ATX_INTERFACE(_object) ((_object)->iface)
00102 
00107 #define ATX_INTERFACE_C(_object,_iface) ((_object)->_iface##_Base.iface)
00108 
00111 #define ATX_CAST(_object, _iface)                   \
00112 (_iface*)ATX_INTERFACE(_object)->GetInterface(      \
00113     _object,                                        \
00114     &ATX_INTERFACE_ID__##_iface)
00115 
00119 #define ATX_INTERFACE_ID(_iface) ATX_INTERFACE_ID__##_iface
00120 
00124 #define ATX_INTERFACE_IDS_EQUAL(_iface_a,_iface_b) \
00125 (((_iface_a)->i0 == (_iface_b)->i0) && ((_iface_a)->i1 == (_iface_b)->i1))
00126 
00127 #define ATX_DECLARE_GET_INTERFACE_IMPLEMENTATION(_class)                     \
00128 static ATX_Object* _class##_GetInterface(_class*                self,        \
00129                                          const ATX_InterfaceId* id);
00130 
00131 #define ATX_BEGIN_GET_INTERFACE_IMPLEMENTATION(_class)                       \
00132 static ATX_Object* _class##_GetInterface(_class*                self,        \
00133                                   const ATX_InterfaceId* id)                 \
00134 {                                                                            \
00135     if (ATX_INTERFACE_IDS_EQUAL(id, &ATX_INTERFACE_ID__ATX_Object)) {        \
00136         return (ATX_Object*)self;                                            \
00137     }
00138 
00139 #define ATX_GET_INTERFACE_ACCEPT(_class, _iface)                             \
00140     else if (ATX_INTERFACE_IDS_EQUAL(id, &ATX_INTERFACE_ID__##_iface)) {     \
00141         return (ATX_Object*)(void*)&(self->_iface##_Base);                   \
00142     }
00143 
00144 #define ATX_GET_INTERFACE_ACCEPT_EX(_class, _base, _iface)                   \
00145     else if (ATX_INTERFACE_IDS_EQUAL(id, &ATX_INTERFACE_ID__##_iface)) {     \
00146         return (ATX_Object*)(void*)&(self->_base##_Base._iface##_Base);      \
00147     }
00148 
00149 #define ATX_END_GET_INTERFACE_IMPLEMENTATION                                 \
00150     else {                                                                   \
00151         return NULL;                                                         \
00152     }                                                                        \
00153 }                                                                            \
00154 
00155 #define ATX_IMPLEMENT_GET_INTERFACE_ADAPTER(_class,_iface)                   \
00156 static ATX_Object*                                                           \
00157 _class##_##_iface##_GetInterface(_iface* _self, const ATX_InterfaceId* id)   \
00158 {                                                                            \
00159     return _class##_GetInterface(ATX_SELF(_class,_iface), id);               \
00160 }
00161 
00162 #define ATX_IMPLEMENT_GET_INTERFACE_ADAPTER_EX(_class,_base,_iface)          \
00163 static ATX_Object*                                                           \
00164 _class##_##_iface##_GetInterface(_iface* _self, const ATX_InterfaceId* id)   \
00165 {                                                                            \
00166     return _class##_GetInterface(ATX_SELF_EX(_class,_base,_iface), id);      \
00167 }
00168 
00169 #define ATX_GET_INTERFACE_ADAPTER(_class, _iface) \
00170 _class##_##_iface##_GetInterface
00171 
00172 #define ATX_INTERFACE_MAP(_class, _iface) \
00173 static const _iface##Interface _class##_##_iface##Interface
00174 
00175 #define ATX_DECLARE_INTERFACE_MAP(_class, _iface) \
00176 ATX_INTERFACE_MAP(_class, _iface);
00177 
00178 #define ATX_BEGIN_INTERFACE_MAP(_class,_iface)      \
00179 ATX_IMPLEMENT_GET_INTERFACE_ADAPTER(_class,_iface)  \
00180 ATX_INTERFACE_MAP(_class,_iface) = {                \
00181     ATX_GET_INTERFACE_ADAPTER(_class,_iface), 
00182 
00183 #define ATX_BEGIN_INTERFACE_MAP_EX(_class, _base, _iface)   \
00184 ATX_IMPLEMENT_GET_INTERFACE_ADAPTER_EX(_class,_base,_iface) \
00185 ATX_INTERFACE_MAP(_class,_iface) = {                        \
00186     ATX_GET_INTERFACE_ADAPTER(_class,_iface), 
00187 
00188 #define ATX_END_INTERFACE_MAP    };
00189 #define ATX_END_INTERFACE_MAP_EX };
00190 
00191 #define ATX_SET_INTERFACE(_object, _class, _iface) \
00192 (_object)->_iface##_Base.iface = & _class##_##_iface##Interface
00193 
00194 #define ATX_SET_INTERFACE_EX(_object, _class, _base, _iface) \
00195 (_object)->_base##_Base._iface##_Base.iface = & _class##_##_iface##Interface
00196 
00197 /*----------------------------------------------------------------------
00198 |   ATX_Object interface
00199 +---------------------------------------------------------------------*/
00208 ATX_DECLARE_INTERFACE(ATX_Object)
00209 ATX_BEGIN_INTERFACE_DEFINITION(ATX_Object)
00210 ATX_END_INTERFACE_DEFINITION
00211 
00212 #endif /* _ATX_INTERFACES_H_ */
00213 
00214 
00215 
00216