fixed warnings in squirrel
[supertux.git] / src / squirrel / squirrel / sqobject.h
1 /*      see copyright notice in squirrel.h */
2 #ifndef _SQOBJECT_H_
3 #define _SQOBJECT_H_
4
5 #include "squtils.h"
6
7 #define SQ_CLOSURESTREAM_HEAD (('S'<<24)|('Q'<<16)|('I'<<8)|('R'))
8 #define SQ_CLOSURESTREAM_PART (('P'<<24)|('A'<<16)|('R'<<8)|('T'))
9 #define SQ_CLOSURESTREAM_TAIL (('T'<<24)|('A'<<16)|('I'<<8)|('L'))
10
11 #define SQ_TRY try
12 #define SQ_CATCH(type, ex) catch(type &ex)
13
14 struct SQSharedState;
15
16 enum SQMetaMethod{
17         MT_ADD=0,
18         MT_SUB=1,
19         MT_MUL=2,
20         MT_DIV=3,
21         MT_UNM=4,
22         MT_MODULO=5,
23         MT_SET=6,
24         MT_GET=7,
25         MT_TYPEOF=8,
26         MT_NEXTI=9,
27         MT_CMP=10,
28         MT_CALL=11,
29         MT_CLONED=12,
30         MT_NEWSLOT=13,
31         MT_DELSLOT=14,
32         MT_LAST = 15,
33 };
34
35 #define MM_ADD          _SC("_add")
36 #define MM_SUB          _SC("_sub")
37 #define MM_MUL          _SC("_mul")
38 #define MM_DIV          _SC("_div")
39 #define MM_UNM          _SC("_unm")
40 #define MM_MODULO       _SC("_modulo")
41 #define MM_SET          _SC("_set")
42 #define MM_GET          _SC("_get")
43 #define MM_TYPEOF       _SC("_typeof")
44 #define MM_NEXTI        _SC("_nexti")
45 #define MM_CMP          _SC("_cmp")
46 #define MM_CALL         _SC("_call")
47 #define MM_CLONED       _SC("_cloned")
48 #define MM_NEWSLOT      _SC("_newslot")
49 #define MM_DELSLOT      _SC("_delslot")
50
51 #define MINPOWER2 4
52
53 struct SQRefCounted
54 {
55         virtual ~SQRefCounted()
56         {}
57         unsigned int _uiRef;
58         virtual void Release()=0;
59 };
60
61 struct SQObjectPtr;
62
63 #define __AddRef(type,unval) if(ISREFCOUNTED(type))     \
64                 { \
65                         unval.pRefCounted->_uiRef++; \
66                 }  
67
68 #define __Release(type,unval) if(ISREFCOUNTED(type) && ((--unval.pRefCounted->_uiRef)<=0))      \
69                 {       \
70                         unval.pRefCounted->Release();   \
71                 }
72
73 #define __ObjRelease(obj) { \
74         if((obj)) {     \
75                 (obj)->_uiRef--; \
76                 if((obj)->_uiRef == 0) \
77                         (obj)->Release(); \
78                 (obj) = NULL;   \
79         } \
80 }
81
82 #define __ObjAddRef(obj) { \
83         (obj)->_uiRef++; \
84 }
85
86 #define type(obj) ((obj)._type)
87 #define is_delegable(t) (type(t)&SQOBJECT_DELEGABLE)
88 #define raw_type(obj) _RAW_TYPE((obj)._type)
89
90 #define _integer(obj) ((obj)._unVal.nInteger)
91 #define _float(obj) ((obj)._unVal.fFloat)
92 #define _string(obj) ((obj)._unVal.pString)
93 #define _table(obj) ((obj)._unVal.pTable)
94 #define _array(obj) ((obj)._unVal.pArray)
95 #define _closure(obj) ((obj)._unVal.pClosure)
96 #define _generator(obj) ((obj)._unVal.pGenerator)
97 #define _nativeclosure(obj) ((obj)._unVal.pNativeClosure)
98 #define _userdata(obj) ((obj)._unVal.pUserData)
99 #define _userpointer(obj) ((obj)._unVal.pUserPointer)
100 #define _thread(obj) ((obj)._unVal.pThread)
101 #define _funcproto(obj) ((obj)._unVal.pFunctionProto)
102 #define _class(obj) ((obj)._unVal.pClass)
103 #define _instance(obj) ((obj)._unVal.pInstance)
104 #define _delegable(obj) ((SQDelegable *)(obj)._unVal.pDelegable)
105 #define _rawval(obj) ((obj)._unVal.pRefCounted)
106
107 #define _stringval(obj) (obj)._unVal.pString->_val
108 #define _userdataval(obj) (obj)._unVal.pUserData->_val
109
110 #define tofloat(num) ((type(num)==OT_INTEGER)?(SQFloat)_integer(num):_float(num))
111 #define tointeger(num) ((type(num)==OT_FLOAT)?(SQInteger)_float(num):_integer(num))
112 /////////////////////////////////////////////////////////////////////////////////////
113 /////////////////////////////////////////////////////////////////////////////////////
114 struct SQObjectPtr : public SQObject
115 {
116         SQObjectPtr()
117         {
118                 _type=OT_NULL;
119                 _unVal.pUserPointer=NULL;
120         }
121         SQObjectPtr(const SQObjectPtr &o)
122         {
123                 _type=o._type;
124                 _unVal=o._unVal;
125                 __AddRef(_type,_unVal);
126         }
127         SQObjectPtr(const SQObject &o)
128         {
129                 _type=o._type;
130                 _unVal=o._unVal;
131                 __AddRef(_type,_unVal);
132         }
133         SQObjectPtr(SQTable *pTable)
134         {
135                 _type=OT_TABLE;
136                 _unVal.pTable=pTable;
137                 assert(_unVal.pTable);
138                 __AddRef(_type,_unVal);
139         }
140         SQObjectPtr(SQClass *pClass)
141         {
142                 _type=OT_CLASS;
143                 _unVal.pClass=pClass;
144                 assert(_unVal.pClass);
145                 __AddRef(_type,_unVal);
146         }
147         SQObjectPtr(SQInstance *pInstance)
148         {
149                 _type=OT_INSTANCE;
150                 _unVal.pInstance=pInstance;
151                 assert(_unVal.pInstance);
152                 __AddRef(_type,_unVal);
153         }
154         SQObjectPtr(SQArray *pArray)
155         {
156                 _type=OT_ARRAY;
157                 _unVal.pArray=pArray;
158                 assert(_unVal.pArray);
159                 __AddRef(_type,_unVal);
160         }
161         SQObjectPtr(SQClosure *pClosure)
162         {
163                 _type=OT_CLOSURE;
164                 _unVal.pClosure=pClosure;
165                 assert(_unVal.pClosure);
166                 __AddRef(_type,_unVal);
167         }
168         SQObjectPtr(SQGenerator *pGenerator)
169         {
170                 _type=OT_GENERATOR;
171                 _unVal.pGenerator=pGenerator;
172                 assert(_unVal.pGenerator);
173                 __AddRef(_type,_unVal);
174         }
175         SQObjectPtr(SQNativeClosure *pNativeClosure)
176         {
177                 _type=OT_NATIVECLOSURE;
178                 _unVal.pNativeClosure=pNativeClosure;
179                 assert(_unVal.pNativeClosure);
180                 __AddRef(_type,_unVal);
181         }
182         SQObjectPtr(SQString *pString)
183         {
184                 _type=OT_STRING;
185                 _unVal.pString=pString;
186                 assert(_unVal.pString);
187                 __AddRef(_type,_unVal);
188         }
189         SQObjectPtr(SQUserData *pUserData)
190         {
191                 _type=OT_USERDATA;
192                 _unVal.pUserData=pUserData;
193                 assert(_unVal.pUserData);
194                 __AddRef(_type,_unVal);
195         }
196         SQObjectPtr(SQVM *pThread)
197         {
198                 _type=OT_THREAD;
199                 _unVal.pThread=pThread;
200                 assert(_unVal.pThread);
201                 __AddRef(_type,_unVal);
202         }
203         SQObjectPtr(SQFunctionProto *pFunctionProto)
204         {
205                 _type=OT_FUNCPROTO;
206                 _unVal.pFunctionProto=pFunctionProto;
207                 assert(_unVal.pFunctionProto);
208                 __AddRef(_type,_unVal);
209         }
210         SQObjectPtr(SQInteger nInteger)
211         {
212                 _type=OT_INTEGER;
213                 _unVal.nInteger=nInteger;
214         }
215         SQObjectPtr(SQFloat fFloat)
216         {
217                 _type=OT_FLOAT;
218                 _unVal.fFloat=fFloat;
219         }
220         SQObjectPtr(bool bBool)
221         {
222                 _type = OT_BOOL;
223                 _unVal.nInteger = bBool?1:0;
224         }
225         SQObjectPtr(SQUserPointer pUserPointer)
226         {
227                 _type=OT_USERPOINTER;
228                 _unVal.pUserPointer=pUserPointer;
229         }
230         ~SQObjectPtr()
231         {
232                 __Release(_type,_unVal);
233         }
234         void Null()
235         {
236                 __Release(_type,_unVal);
237                 _type=OT_NULL;
238                 _unVal.pUserPointer=NULL;
239         }
240         SQObjectPtr& operator=(const SQObjectPtr& obj)
241         { 
242                 SQObjectType tOldType;
243                 SQObjectValue unOldVal;
244                 tOldType=_type;
245                 unOldVal=_unVal;
246                 _unVal = obj._unVal;
247                 _type = obj._type;
248                 __AddRef(_type,_unVal);
249                 __Release(tOldType,unOldVal);
250                 return *this;
251         }
252         SQObjectPtr& operator=(const SQObject& obj)
253         { 
254                 SQObjectType tOldType;
255                 SQObjectValue unOldVal;
256                 tOldType=_type;
257                 unOldVal=_unVal;
258                 _unVal = obj._unVal;
259                 _type = obj._type;
260                 __AddRef(_type,_unVal);
261                 __Release(tOldType,unOldVal);
262                 return *this;
263         }
264         private:
265                 SQObjectPtr(const SQChar *){} //safety
266 };
267 /////////////////////////////////////////////////////////////////////////////////////
268 #ifndef NO_GARBAGE_COLLECTOR
269 #define MARK_FLAG 0x80000000
270 struct SQCollectable : public SQRefCounted {
271         SQCollectable *_next;
272         SQCollectable *_prev;
273         SQSharedState *_sharedstate;
274         virtual void Release()=0;
275         virtual void Mark(SQCollectable **chain)=0;
276         void UnMark();
277         virtual void Finalize()=0;
278         static void AddToChain(SQCollectable **chain,SQCollectable *c);
279         static void RemoveFromChain(SQCollectable **chain,SQCollectable *c);
280 };
281
282
283 #define ADD_TO_CHAIN(chain,obj) AddToChain(chain,obj)
284 #define REMOVE_FROM_CHAIN(chain,obj) {if(!(_uiRef&MARK_FLAG))RemoveFromChain(chain,obj);}
285 #define CHAINABLE_OBJ SQCollectable
286 #define INIT_CHAIN() {_next=NULL;_prev=NULL;_sharedstate=ss;}
287 #else
288
289 #define ADD_TO_CHAIN(chain,obj) ((void)0)
290 #define REMOVE_FROM_CHAIN(chain,obj) ((void)0)
291 #define CHAINABLE_OBJ SQRefCounted
292 #define INIT_CHAIN() ((void)0)
293 #endif
294
295 struct SQDelegable : public CHAINABLE_OBJ {
296         virtual bool GetMetaMethod(SQMetaMethod mm,SQObjectPtr &res);
297         SQTable *_delegate;
298 };
299
300 unsigned int TranslateIndex(const SQObjectPtr &idx);
301 typedef sqvector<SQObjectPtr> SQObjectPtrVec;
302 typedef sqvector<int> SQIntVec;
303
304 #endif //_SQOBJECT_H_