1 /* ScummVM - Graphic Adventure Engine
2  *
3  * ScummVM is the legal property of its developers, whose names
4  * are too numerous to list here. Please refer to the COPYRIGHT
5  * file distributed with this source distribution.
6  *
7  * This program is free software; you can redistribute it and/or
8  * modify it under the terms of the GNU General Public License
9  * as published by the Free Software Foundation; either version 2
10  * of the License, or (at your option) any later version.
11  *
12  * This program is distributed in the hope that it will be useful,
13  * but WITHOUT ANY WARRANTY; without even the implied warranty of
14  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
15  * GNU General Public License for more details.
16  *
17  * You should have received a copy of the GNU General Public License
18  * along with this program; if not, write to the Free Software
19  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
20  *
21  */
22 
23 //=============================================================================
24 //
25 // Script API function type and helper macros for forwarding runtime script
26 // values to real engine functions.
27 //
28 //=============================================================================
29 
30 #ifndef AGS_ENGINE_SCRIPT_SCRIPT_API_H
31 #define AGS_ENGINE_SCRIPT_SCRIPT_API_H
32 
33 //include <stdarg.h>
34 #include "ags/shared/core/types.h"
35 #include "ags/engine/ac/runtime_defines.h"
36 #include "ags/engine/ac/statobj/ags_static_object.h"
37 #include "ags/shared/debugging/out.h"
38 
39 namespace AGS3 {
40 
41 struct RuntimeScriptValue;
42 
43 // TODO: replace void* with base object class when possible; also put array class for parameters
44 typedef RuntimeScriptValue ScriptAPIFunction(const RuntimeScriptValue *params, int32_t param_count);
45 typedef RuntimeScriptValue ScriptAPIObjectFunction(void *self, const RuntimeScriptValue *params, int32_t param_count);
46 
47 // Sprintf that takes either script values or common argument list from plugin.
48 // Uses EITHER sc_args/sc_argc or varg_ptr as parameter list, whichever is not
49 // NULL, with varg_ptr having HIGHER priority.
50 const char *ScriptSprintf(char *buffer, size_t buf_length, const char *format,
51                           const RuntimeScriptValue *sc_args, int32_t sc_argc, va_list *varg_ptr);
52 // Sprintf that takes script values as arguments
ScriptSprintf(char * buffer,size_t buf_length,const char * format,const RuntimeScriptValue * args,int32_t argc)53 inline const char *ScriptSprintf(char *buffer, size_t buf_length, const char *format, const RuntimeScriptValue *args, int32_t argc) {
54 	return ScriptSprintf(buffer, buf_length, format, args, argc, nullptr);
55 }
56 // Variadic sprintf (needed, because all arguments are pushed as pointer-sized values). Currently used only when plugin calls
57 // exported engine function. Should be removed when this plugin issue is resolved.
ScriptVSprintf(char * buffer,size_t buf_length,const char * format,va_list & arg_ptr)58 inline const char *ScriptVSprintf(char *buffer, size_t buf_length, const char *format, va_list &arg_ptr) {
59 	return ScriptSprintf(buffer, buf_length, format, nullptr, 0, &arg_ptr);
60 }
61 
62 // Helper macros for script functions
63 #define ASSERT_SELF(METHOD) \
64 	assert((self != NULL) && "Object pointer is null in call to API function")
65 #define ASSERT_PARAM_COUNT(FUNCTION, X) \
66 	assert((params != NULL && param_count >= X) && "Not enough parameters in call to API function")
67 #define ASSERT_VARIABLE_VALUE(VARIABLE) \
68 	assert((params != NULL && param_count >= 1) && "Not enough parameters to set API property")
69 #define ASSERT_OBJ_PARAM_COUNT(METHOD, X) \
70 	ASSERT_SELF(METHOD); \
71 	ASSERT_PARAM_COUNT(METHOD, X)
72 
73 //-----------------------------------------------------------------------------
74 // Get/set variables
75 
76 #define API_VARGET_INT(VARIABLE) \
77 	return RuntimeScriptValue().SetInt32(VARIABLE)
78 
79 #define API_VARSET_PINT(VARIABLE) \
80 	ASSERT_VARIABLE_VALUE(VARIABLE); \
81 	VARIABLE = params[0].IValue; \
82 	return RuntimeScriptValue()
83 
84 //-----------------------------------------------------------------------------
85 // Calls to ScriptSprintf with automatic translation
86 
87 #define API_SCALL_SCRIPT_SPRINTF(FUNCTION, PARAM_COUNT) \
88 	ASSERT_PARAM_COUNT(FUNCTION, PARAM_COUNT); \
89 	char ScSfBuffer[STD_BUFFER_SIZE]; \
90 	const char *scsf_buffer = ScriptSprintf(ScSfBuffer, STD_BUFFER_SIZE, get_translation(params[PARAM_COUNT - 1].Ptr), params + PARAM_COUNT, param_count - PARAM_COUNT)
91 
92 #define API_OBJCALL_SCRIPT_SPRINTF(METHOD, PARAM_COUNT) \
93 	ASSERT_OBJ_PARAM_COUNT(METHOD, PARAM_COUNT); \
94 	char ScSfBuffer[STD_BUFFER_SIZE]; \
95 	const char *scsf_buffer = ScriptSprintf(ScSfBuffer, STD_BUFFER_SIZE, get_translation(params[PARAM_COUNT - 1].Ptr), params + PARAM_COUNT, param_count - PARAM_COUNT)
96 
97 //-----------------------------------------------------------------------------
98 // Calls to ScriptSprintf without translation
99 
100 #define API_SCALL_SCRIPT_SPRINTF_PURE(FUNCTION, PARAM_COUNT) \
101     ASSERT_PARAM_COUNT(FUNCTION, PARAM_COUNT); \
102     char ScSfBuffer[STD_BUFFER_SIZE]; \
103     const char *scsf_buffer = ScriptSprintf(ScSfBuffer, STD_BUFFER_SIZE, params[PARAM_COUNT - 1].Ptr, params + PARAM_COUNT, param_count - PARAM_COUNT)
104 
105 
106 //-----------------------------------------------------------------------------
107 // Calls to ScriptSprintfV (unsafe plugin variant)
108 
109 #define API_PLUGIN_SCRIPT_SPRINTF(FORMAT_STR) \
110 	va_list args; \
111 	va_start(args, FORMAT_STR); \
112 	char ScSfBuffer[STD_BUFFER_SIZE]; \
113 	const char *scsf_buffer = ScriptVSprintf(ScSfBuffer, STD_BUFFER_SIZE, get_translation(FORMAT_STR), args); \
114 	va_end(args)
115 
116 //-----------------------------------------------------------------------------
117 // Calls to static functions
118 //
119 // IMPORTANT: please note following: historically AGS compiler did not have
120 // proper "void" type and allowed to store the return value of "void" API
121 // functions as an integer (although that value did not have any practical
122 // meaning). For backwards compatibility we actually return integer value
123 // of '0' in all the VOID script API functions!
124 //
125 
126 #define API_SCALL_VOID(FUNCTION) \
127 	FUNCTION(); \
128 	return RuntimeScriptValue((int32_t)0)
129 
130 #define API_SCALL_VOID_PBOOL(FUNCTION) \
131 	ASSERT_PARAM_COUNT(FUNCTION, 1); \
132 	FUNCTION(params[0].GetAsBool()); \
133 	return RuntimeScriptValue((int32_t)0)
134 
135 #define API_SCALL_VOID_PINT(FUNCTION) \
136 	ASSERT_PARAM_COUNT(FUNCTION, 1); \
137 	FUNCTION(params[0].IValue); \
138 	return RuntimeScriptValue((int32_t)0)
139 
140 #define API_SCALL_VOID_PINT2(FUNCTION) \
141 	ASSERT_PARAM_COUNT(FUNCTION, 2); \
142 	FUNCTION(params[0].IValue, params[1].IValue); \
143 	return RuntimeScriptValue((int32_t)0)
144 
145 #define API_SCALL_VOID_PINT3(FUNCTION) \
146 	ASSERT_PARAM_COUNT(FUNCTION, 3); \
147 	FUNCTION(params[0].IValue, params[1].IValue, params[2].IValue); \
148 	return RuntimeScriptValue((int32_t)0)
149 
150 #define API_SCALL_VOID_PINT4(FUNCTION) \
151 	ASSERT_PARAM_COUNT(FUNCTION, 4); \
152 	FUNCTION(params[0].IValue, params[1].IValue, params[2].IValue, params[3].IValue); \
153 	return RuntimeScriptValue((int32_t)0)
154 
155 #define API_SCALL_VOID_PINT5(FUNCTION) \
156 	ASSERT_PARAM_COUNT(FUNCTION, 5); \
157 	FUNCTION(params[0].IValue, params[1].IValue, params[2].IValue, params[3].IValue, params[4].IValue); \
158 	return RuntimeScriptValue((int32_t)0)
159 
160 #define API_SCALL_VOID_PINT6(FUNCTION) \
161 	ASSERT_PARAM_COUNT(FUNCTION, 6); \
162 	FUNCTION(params[0].IValue, params[1].IValue, params[2].IValue, params[3].IValue, params[4].IValue, params[5].IValue); \
163 	return RuntimeScriptValue((int32_t)0)
164 
165 #define API_SCALL_VOID_PINT_POBJ(FUNCTION, P1CLASS) \
166 	ASSERT_PARAM_COUNT(FUNCTION, 2); \
167 	FUNCTION(params[0].IValue, (P1CLASS*)params[1].Ptr); \
168 	return RuntimeScriptValue((int32_t)0)
169 
170 #define API_SCALL_VOID_PINT_POBJ2(FUNCTION, P1CLASS, P2CLASS) \
171 	ASSERT_PARAM_COUNT(FUNCTION, 3); \
172 	FUNCTION(params[0].IValue, (P1CLASS*)params[1].Ptr, (P2CLASS*)params[2].Ptr); \
173 	return RuntimeScriptValue((int32_t)0)
174 
175 #define API_SCALL_VOID_PINT2_POBJ(FUNCTION, P1CLASS) \
176 	ASSERT_PARAM_COUNT(FUNCTION, 3); \
177 	FUNCTION(params[0].IValue, params[1].IValue, (P1CLASS*)params[2].Ptr); \
178 	return RuntimeScriptValue((int32_t)0)
179 
180 #define API_SCALL_VOID_PINT3_POBJ_PINT(FUNCTION, P1CLASS) \
181 	ASSERT_PARAM_COUNT(FUNCTION, 5); \
182 	FUNCTION(params[0].IValue, params[1].IValue, params[2].IValue, (P1CLASS*)params[3].Ptr, params[4].IValue); \
183 	return RuntimeScriptValue((int32_t)0)
184 
185 #define API_SCALL_VOID_PINT4_POBJ(FUNCTION, P1CLASS) \
186 	ASSERT_PARAM_COUNT(FUNCTION, 5); \
187 	FUNCTION(params[0].IValue, params[1].IValue, params[2].IValue, params[3].IValue, (P1CLASS*)params[4].Ptr); \
188 	return RuntimeScriptValue((int32_t)0)
189 
190 #define API_SCALL_VOID_PFLOAT2(FUNCTION) \
191 	ASSERT_PARAM_COUNT(FUNCTION, 2); \
192 	FUNCTION(params[0].FValue, params[1].FValue); \
193 	return RuntimeScriptValue((int32_t)0)
194 
195 #define API_SCALL_VOID_POBJ(FUNCTION, P1CLASS) \
196 	ASSERT_PARAM_COUNT(FUNCTION, 1); \
197 	FUNCTION((P1CLASS*)params[0].Ptr); \
198 	return RuntimeScriptValue((int32_t)0)
199 
200 #define API_SCALL_VOID_POBJ_PINT(FUNCTION, P1CLASS) \
201 	ASSERT_PARAM_COUNT(FUNCTION, 2); \
202 	FUNCTION((P1CLASS*)params[0].Ptr, params[1].IValue); \
203 	return RuntimeScriptValue((int32_t)0)
204 
205 #define API_SCALL_VOID_POBJ_PINT2(FUNCTION, P1CLASS) \
206 	ASSERT_PARAM_COUNT(FUNCTION, 3); \
207 	FUNCTION((P1CLASS*)params[0].Ptr, params[1].IValue, params[2].IValue); \
208 	return RuntimeScriptValue((int32_t)0)
209 
210 #define API_SCALL_VOID_POBJ2(FUNCTION, P1CLASS, P2CLASS) \
211 	ASSERT_PARAM_COUNT(FUNCTION, 2); \
212 	FUNCTION((P1CLASS*)params[0].Ptr, (P2CLASS*)params[1].Ptr); \
213 	return RuntimeScriptValue((int32_t)0)
214 
215 #define API_SCALL_INT(FUNCTION) \
216 	return RuntimeScriptValue().SetInt32(FUNCTION())
217 
218 #define API_SCALL_INT_PINT(FUNCTION) \
219 	ASSERT_PARAM_COUNT(FUNCTION, 1); \
220 	return RuntimeScriptValue().SetInt32(FUNCTION(params[0].IValue))
221 
222 #define API_SCALL_INT_PINT2(FUNCTION) \
223 	ASSERT_PARAM_COUNT(FUNCTION, 2); \
224 	return RuntimeScriptValue().SetInt32(FUNCTION(params[0].IValue, params[1].IValue))
225 
226 #define API_SCALL_INT_PINT3(FUNCTION) \
227 	ASSERT_PARAM_COUNT(FUNCTION, 3); \
228 	return RuntimeScriptValue().SetInt32(FUNCTION(params[0].IValue, params[1].IValue, params[2].IValue))
229 
230 #define API_SCALL_INT_PINT4(FUNCTION) \
231 	ASSERT_PARAM_COUNT(FUNCTION, 4); \
232 	return RuntimeScriptValue().SetInt32(FUNCTION(params[0].IValue, params[1].IValue, params[2].IValue, params[3].IValue))
233 
234 #define API_SCALL_INT_PINT4_PFLOAT(FUNCTION) \
235 	ASSERT_PARAM_COUNT(FUNCTION, 5) \
236 	return RuntimeScriptValue().SetInt32(FUNCTION(params[0].IValue, params[1].IValue, params[2].IValue, params[3].IValue, params[3].FValue))
237 
238 #define API_SCALL_INT_PINT5(FUNCTION) \
239 	ASSERT_PARAM_COUNT(FUNCTION, 5); \
240 	return RuntimeScriptValue().SetInt32(FUNCTION(params[0].IValue, params[1].IValue, params[2].IValue, params[3].IValue, params[4].IValue))
241 
242 #define API_SCALL_INT_PFLOAT_PINT(FUNCTION) \
243 	ASSERT_PARAM_COUNT(FUNCTION, 2); \
244 	return RuntimeScriptValue().SetInt32(FUNCTION(params[0].FValue, params[1].IValue))
245 
246 #define API_SCALL_INT_POBJ(FUNCTION, P1CLASS) \
247 	ASSERT_PARAM_COUNT(FUNCTION, 1); \
248 	return RuntimeScriptValue().SetInt32(FUNCTION((P1CLASS*)params[0].Ptr))
249 
250 #define API_SCALL_INT_POBJ_PINT(FUNCTION, P1CLASS) \
251 	ASSERT_PARAM_COUNT(FUNCTION, 2); \
252 	return RuntimeScriptValue().SetInt32(FUNCTION((P1CLASS*)params[0].Ptr, params[1].IValue))
253 
254 #define API_SCALL_INT_POBJ_PINT2(FUNCTION, P1CLASS) \
255 	ASSERT_PARAM_COUNT(FUNCTION, 3); \
256 	return RuntimeScriptValue().SetInt32(FUNCTION((P1CLASS*)params[0].Ptr, params[1].IValue, params[2].IValue))
257 
258 #define API_SCALL_INT_POBJ2(FUNCTION, P1CLASS, P2CLASS) \
259 	ASSERT_PARAM_COUNT(FUNCTION, 2); \
260 	return RuntimeScriptValue().SetInt32(FUNCTION((P1CLASS*)params[0].Ptr, (P2CLASS*)params[1].Ptr))
261 
262 #define API_SCALL_INT_PINT_POBJ(FUNCTION, P1CLASS) \
263 	ASSERT_PARAM_COUNT(FUNCTION, 2); \
264 	return RuntimeScriptValue().SetInt32(FUNCTION(params[0].IValue, (P1CLASS*)params[1].Ptr))
265 
266 #define API_SCALL_FLOAT(FUNCTION) \
267 	return RuntimeScriptValue().SetFloat(FUNCTION())
268 
269 #define API_SCALL_FLOAT_PINT(FUNCTION) \
270 	ASSERT_PARAM_COUNT(FUNCTION, 1); \
271 	return RuntimeScriptValue().SetFloat(FUNCTION(params[0].IValue))
272 
273 #define API_SCALL_FLOAT_PFLOAT(FUNCTION) \
274 	ASSERT_PARAM_COUNT(FUNCTION, 1); \
275 	return RuntimeScriptValue().SetFloat(FUNCTION(params[0].FValue))
276 
277 #define API_SCALL_FLOAT_PFLOAT2(FUNCTION) \
278 	ASSERT_PARAM_COUNT(FUNCTION, 2); \
279 	return RuntimeScriptValue().SetFloat(FUNCTION(params[0].FValue, params[1].FValue))
280 
281 #define API_SCALL_BOOL(FUNCTION) \
282 	return RuntimeScriptValue().SetInt32AsBool(FUNCTION())
283 
284 #define API_SCALL_BOOL_OBJ(FUNCTION, P1CLASS) \
285 	ASSERT_PARAM_COUNT(FUNCTION, 1); \
286 	return RuntimeScriptValue().SetInt32AsBool(FUNCTION((P1CLASS*)params[0].Ptr))
287 
288 #define API_SCALL_BOOL_PINT(FUNCTION) \
289     ASSERT_PARAM_COUNT(FUNCTION, 1); \
290     return RuntimeScriptValue().SetInt32AsBool(FUNCTION(params[0].IValue))
291 
292 #define API_SCALL_BOOL_POBJ_PINT(FUNCTION, P1CLASS) \
293 	ASSERT_PARAM_COUNT(FUNCTION, 2); \
294 	return RuntimeScriptValue().SetInt32AsBool(FUNCTION((P1CLASS*)params[0].Ptr, params[1].IValue))
295 
296 #define API_SCALL_BOOL_POBJ2(FUNCTION, P1CLASS, P2CLASS) \
297 	ASSERT_PARAM_COUNT(FUNCTION, 2); \
298 	return RuntimeScriptValue().SetInt32AsBool(FUNCTION((P1CLASS*)params[0].Ptr, (P2CLASS*)params[1].Ptr))
299 
300 #define API_SCALL_OBJ(RET_CLASS, RET_MGR, FUNCTION) \
301 	return RuntimeScriptValue().SetDynamicObject((void*)(RET_CLASS*)FUNCTION(), &RET_MGR)
302 
303 #define API_CONST_SCALL_OBJ(RET_CLASS, RET_MGR, FUNCTION) \
304 	return RuntimeScriptValue().SetDynamicObject(const_cast<void *>((const void *)(RET_CLASS*)FUNCTION()), &RET_MGR)
305 
306 #define API_SCALL_OBJ_PINT(RET_CLASS, RET_MGR, FUNCTION) \
307 	ASSERT_PARAM_COUNT(FUNCTION, 1); \
308 	return RuntimeScriptValue().SetDynamicObject((void*)(RET_CLASS*)FUNCTION(params[0].IValue), &RET_MGR)
309 
310 #define API_CONST_SCALL_OBJ_PINT(RET_CLASS, RET_MGR, FUNCTION) \
311 	ASSERT_PARAM_COUNT(FUNCTION, 1); \
312 	return RuntimeScriptValue().SetDynamicObject(const_cast<void *>((const void *)(RET_CLASS*)FUNCTION(params[0].IValue)), &RET_MGR)
313 
314 #define API_SCALL_OBJ_POBJ_PINT_PBOOL(RET_CLASS, RET_MGR, FUNCTION, P1CLASS) \
315 	ASSERT_PARAM_COUNT(FUNCTION, 3); \
316 	return RuntimeScriptValue().SetDynamicObject((void*)(RET_CLASS*)FUNCTION((P1CLASS*)params[0].Ptr, params[1].IValue, params[2].GetAsBool()), &RET_MGR)
317 
318 #define API_SCALL_OBJ_PINT2(RET_CLASS, RET_MGR, FUNCTION) \
319 	ASSERT_PARAM_COUNT(FUNCTION, 2); \
320 	return RuntimeScriptValue().SetDynamicObject((void*)(RET_CLASS*)FUNCTION(params[0].IValue, params[1].IValue), &RET_MGR)
321 
322 #define API_CONST_SCALL_OBJ_PINT2(RET_CLASS, RET_MGR, FUNCTION) \
323 	ASSERT_PARAM_COUNT(FUNCTION, 2); \
324 	return RuntimeScriptValue().SetDynamicObject(const_cast<void *>((const void *)(RET_CLASS*)FUNCTION(params[0].IValue, params[1].IValue)), &RET_MGR)
325 
326 #define API_SCALL_OBJ_PINT3_POBJ(RET_CLASS, RET_MGR, FUNCTION, P1CLASS) \
327 	ASSERT_PARAM_COUNT(FUNCTION, 4); \
328 	return RuntimeScriptValue().SetDynamicObject((void*)(RET_CLASS*)FUNCTION(params[0].IValue, params[1].IValue, params[2].IValue, (P1CLASS*)params[3].Ptr), &RET_MGR)
329 
330 #define API_SCALL_OBJ_POBJ(RET_CLASS, RET_MGR, FUNCTION, P1CLASS) \
331 	ASSERT_PARAM_COUNT(FUNCTION, 1); \
332 	return RuntimeScriptValue().SetDynamicObject((void*)(RET_CLASS*)FUNCTION((P1CLASS*)params[0].Ptr), &RET_MGR)
333 
334 #define API_CONST_SCALL_OBJ_POBJ(RET_CLASS, RET_MGR, FUNCTION, P1CLASS) \
335 	ASSERT_PARAM_COUNT(FUNCTION, 1); \
336 	return RuntimeScriptValue().SetDynamicObject(const_cast<void *>((const void *)(RET_CLASS*)FUNCTION((P1CLASS*)params[0].Ptr)), &RET_MGR)
337 
338 #define API_SCALL_OBJAUTO(RET_CLASS, FUNCTION) \
339 	RET_CLASS* ret_obj = FUNCTION(); \
340 	return RuntimeScriptValue().SetDynamicObject(ret_obj, ret_obj)
341 
342 #define API_SCALL_OBJAUTO_PINT(RET_CLASS, FUNCTION) \
343 	ASSERT_PARAM_COUNT(FUNCTION, 1); \
344 	RET_CLASS* ret_obj = FUNCTION(params[0].IValue); \
345 	return RuntimeScriptValue().SetDynamicObject(ret_obj, ret_obj)
346 
347 #define API_SCALL_OBJAUTO_PINT2(RET_CLASS, FUNCTION) \
348 	ASSERT_PARAM_COUNT(FUNCTION, 2); \
349 	RET_CLASS* ret_obj = FUNCTION(params[0].IValue, params[1].IValue); \
350 	return RuntimeScriptValue().SetDynamicObject(ret_obj, ret_obj)
351 
352 #define API_SCALL_OBJAUTO_PINT3(RET_CLASS, FUNCTION) \
353 	ASSERT_PARAM_COUNT(FUNCTION, 3); \
354 	RET_CLASS* ret_obj = FUNCTION(params[0].IValue, params[1].IValue, params[2].IValue); \
355 	return RuntimeScriptValue().SetDynamicObject(ret_obj, ret_obj)
356 
357 #define API_SCALL_OBJAUTO_PINT4(RET_CLASS, FUNCTION) \
358 	ASSERT_PARAM_COUNT(FUNCTION, 4); \
359 	RET_CLASS* ret_obj = FUNCTION(params[0].IValue, params[1].IValue, params[2].IValue, params[3].IValue); \
360 	return RuntimeScriptValue().SetDynamicObject(ret_obj, ret_obj)
361 
362 #define API_SCALL_OBJAUTO_PINT5(RET_CLASS, FUNCTION) \
363 	ASSERT_PARAM_COUNT(FUNCTION, 5); \
364 	RET_CLASS* ret_obj = FUNCTION(params[0].IValue, params[1].IValue, params[2].IValue, params[3].IValue, params[4].IValue); \
365 	return RuntimeScriptValue().SetDynamicObject(ret_obj, ret_obj)
366 
367 #define API_SCALL_OBJAUTO_PBOOL2(RET_CLASS, FUNCTION) \
368 	ASSERT_PARAM_COUNT(FUNCTION, 2); \
369 	RET_CLASS* ret_obj = FUNCTION(params[0].GetAsBool(), params[1].GetAsBool()); \
370 	return RuntimeScriptValue().SetDynamicObject(ret_obj, ret_obj)
371 
372 #define API_SCALL_OBJAUTO_POBJ(RET_CLASS, FUNCTION, P1CLASS) \
373 	ASSERT_PARAM_COUNT(FUNCTION, 1); \
374 	RET_CLASS* ret_obj = FUNCTION((P1CLASS*)params[0].Ptr); \
375 	return RuntimeScriptValue().SetDynamicObject(ret_obj, ret_obj)
376 
377 #define API_SCALL_OBJAUTO_POBJ_PINT(RET_CLASS, FUNCTION, P1CLASS) \
378 	ASSERT_PARAM_COUNT(FUNCTION, 2); \
379 	RET_CLASS* ret_obj = (RET_CLASS*)FUNCTION((P1CLASS*)params[0].Ptr, params[1].IValue); \
380 	return RuntimeScriptValue().SetDynamicObject(ret_obj, ret_obj)
381 
382 #define API_SCALL_OBJAUTO_POBJ_PINT4(RET_CLASS, FUNCTION, P1CLASS) \
383 	ASSERT_PARAM_COUNT(FUNCTION, 5); \
384 	RET_CLASS* ret_obj = FUNCTION((P1CLASS*)params[0].Ptr, params[1].IValue, params[2].IValue, params[3].IValue, params[4].IValue); \
385 	return RuntimeScriptValue().SetDynamicObject(ret_obj, ret_obj)
386 
387 
388 #define API_SCALL_STOBJ_POBJ2(RET_CLASS, FUNCTION, P1CLASS, P2CLASS) \
389 	ASSERT_PARAM_COUNT(FUNCTION, 2); \
390 	RET_CLASS* ret_obj = FUNCTION((P1CLASS*)params[0].Ptr, (P2CLASS*)params[1].Ptr); \
391 	return RuntimeScriptValue().SetStaticObject(ret_obj, &_GP(GlobalStaticManager))
392 
393 //-----------------------------------------------------------------------------
394 // Calls to object functions
395 
396 #define API_OBJCALL_VOID(CLASS, METHOD) \
397 	ASSERT_SELF(METHOD); \
398 	METHOD((CLASS*)self); \
399 	return RuntimeScriptValue((int32_t)0)
400 
401 #define API_OBJCALL_VOID_PINT(CLASS, METHOD) \
402 	ASSERT_OBJ_PARAM_COUNT(METHOD, 1); \
403 	METHOD((CLASS*)self, params[0].IValue); \
404 	return RuntimeScriptValue((int32_t)0)
405 
406 #define API_OBJCALL_VOID_PINT2(CLASS, METHOD) \
407 	ASSERT_OBJ_PARAM_COUNT(METHOD, 2); \
408 	METHOD((CLASS*)self, params[0].IValue, params[1].IValue); \
409 	return RuntimeScriptValue((int32_t)0)
410 
411 #define API_OBJCALL_VOID_PINT3(CLASS, METHOD) \
412 	ASSERT_OBJ_PARAM_COUNT(METHOD, 3); \
413 	METHOD((CLASS*)self, params[0].IValue, params[1].IValue, params[2].IValue); \
414 	return RuntimeScriptValue((int32_t)0)
415 
416 #define API_OBJCALL_VOID_PINT4(CLASS, METHOD) \
417 	ASSERT_OBJ_PARAM_COUNT(METHOD, 4); \
418 	METHOD((CLASS*)self, params[0].IValue, params[1].IValue, params[2].IValue, params[3].IValue); \
419 	return RuntimeScriptValue((int32_t)0)
420 
421 #define API_OBJCALL_VOID_PINT5(CLASS, METHOD) \
422 	ASSERT_OBJ_PARAM_COUNT(METHOD, 5); \
423 	METHOD((CLASS*)self, params[0].IValue, params[1].IValue, params[2].IValue, params[3].IValue, params[4].IValue); \
424 	return RuntimeScriptValue((int32_t)0)
425 
426 #define API_OBJCALL_VOID_PINT6(CLASS, METHOD) \
427 	ASSERT_OBJ_PARAM_COUNT(METHOD, 6); \
428 	METHOD((CLASS*)self, params[0].IValue, params[1].IValue, params[2].IValue, params[3].IValue, params[4].IValue, params[5].IValue); \
429 	return RuntimeScriptValue((int32_t)0)
430 
431 #define API_OBJCALL_VOID_PFLOAT(CLASS, METHOD) \
432 	ASSERT_OBJ_PARAM_COUNT(METHOD, 1); \
433 	METHOD((CLASS*)self, params[0].FValue); \
434 	return RuntimeScriptValue()
435 
436 #define API_OBJCALL_VOID_PFLOAT2(CLASS, METHOD) \
437 	ASSERT_OBJ_PARAM_COUNT(METHOD, 2); \
438 	METHOD((CLASS*)self, params[0].FValue, params[1].FValue); \
439 	return RuntimeScriptValue()
440 
441 #define API_OBJCALL_VOID_PBOOL(CLASS, METHOD) \
442 	ASSERT_OBJ_PARAM_COUNT(METHOD, 1); \
443 	METHOD((CLASS*)self, params[0].GetAsBool()); \
444 	return RuntimeScriptValue((int32_t)0)
445 
446 #define API_OBJCALL_VOID_PINT_PBOOL(CLASS, METHOD) \
447 	ASSERT_OBJ_PARAM_COUNT(METHOD, 2); \
448 	METHOD((CLASS*)self, params[0].IValue, params[1].GetAsBool()); \
449 	return RuntimeScriptValue((int32_t)0)
450 
451 #define API_OBJCALL_VOID_PINT_POBJ(CLASS, METHOD, P1CLASS) \
452 	ASSERT_OBJ_PARAM_COUNT(METHOD, 2); \
453 	METHOD((CLASS*)self, params[0].IValue, (P1CLASS*)params[1].Ptr); \
454 	return RuntimeScriptValue((int32_t)0)
455 
456 #define API_OBJCALL_VOID_PINT3_POBJ(CLASS, METHOD, P1CLASS) \
457 	ASSERT_OBJ_PARAM_COUNT(METHOD, 4); \
458 	METHOD((CLASS*)self, params[0].IValue, params[1].IValue, params[2].IValue, (P1CLASS*)params[3].Ptr); \
459 	return RuntimeScriptValue((int32_t)0)
460 
461 #define API_OBJCALL_VOID_PINT5_POBJ(CLASS, METHOD, P1CLASS) \
462 	ASSERT_OBJ_PARAM_COUNT(METHOD, 6); \
463 	METHOD((CLASS*)self, params[0].IValue, params[1].IValue, params[2].IValue, params[3].IValue, params[4].IValue, (P1CLASS*)params[5].Ptr); \
464 	return RuntimeScriptValue((int32_t)0)
465 
466 #define API_OBJCALL_VOID_POBJ(CLASS, METHOD, P1CLASS) \
467 	ASSERT_OBJ_PARAM_COUNT(METHOD, 1); \
468 	METHOD((CLASS*)self, (P1CLASS*)params[0].Ptr); \
469 	return RuntimeScriptValue((int32_t)0)
470 
471 #define API_OBJCALL_VOID_POBJ_PINT(CLASS, METHOD, P1CLASS) \
472 	ASSERT_OBJ_PARAM_COUNT(METHOD, 2); \
473 	METHOD((CLASS*)self, (P1CLASS*)params[0].Ptr, params[1].IValue); \
474 	return RuntimeScriptValue((int32_t)0)
475 
476 #define API_OBJCALL_VOID_POBJ_PINT2(CLASS, METHOD, P1CLASS) \
477 	ASSERT_OBJ_PARAM_COUNT(METHOD, 3); \
478 	METHOD((CLASS*)self, (P1CLASS*)params[0].Ptr, params[1].IValue, params[2].IValue); \
479 	return RuntimeScriptValue((int32_t)0)
480 
481 #define API_OBJCALL_VOID_POBJ2(CLASS, METHOD, P1CLASS, P2CLASS) \
482 	ASSERT_OBJ_PARAM_COUNT(METHOD, 2); \
483 	METHOD((CLASS*)self, (P1CLASS*)params[0].Ptr, (P2CLASS*)params[1].Ptr); \
484 	return RuntimeScriptValue((int32_t)0)
485 
486 #define API_OBJCALL_INT(CLASS, METHOD) \
487 	ASSERT_SELF(METHOD); \
488 	return RuntimeScriptValue().SetInt32(METHOD((CLASS*)self))
489 
490 #define API_OBJCALL_INT_PINT(CLASS, METHOD) \
491 	ASSERT_OBJ_PARAM_COUNT(METHOD, 1); \
492 	return RuntimeScriptValue().SetInt32(METHOD((CLASS*)self, params[0].IValue))
493 
494 #define API_OBJCALL_INT_PINT_POBJ(CLASS, METHOD, P1CLASS) \
495 	ASSERT_OBJ_PARAM_COUNT(METHOD, 2); \
496 	return RuntimeScriptValue().SetInt32(METHOD((CLASS*)self, params[0].IValue, params[1].Ptr))
497 
498 #define API_OBJCALL_INT_PINT2(CLASS, METHOD) \
499 	ASSERT_OBJ_PARAM_COUNT(METHOD, 2); \
500 	return RuntimeScriptValue().SetInt32(METHOD((CLASS*)self, params[0].IValue, params[1].IValue))
501 
502 #define API_OBJCALL_INT_POBJ(CLASS, METHOD, P1CLASS) \
503 	ASSERT_OBJ_PARAM_COUNT(METHOD, 1); \
504 	return RuntimeScriptValue().SetInt32(METHOD((CLASS*)self, (P1CLASS*)params[0].Ptr))
505 
506 #define API_OBJCALL_INT_POBJ_PINT(CLASS, METHOD, P1CLASS) \
507 	ASSERT_OBJ_PARAM_COUNT(METHOD, 2); \
508 	return RuntimeScriptValue().SetInt32(METHOD((CLASS*)self, (P1CLASS*)params[0].Ptr, params[1].IValue))
509 
510 #define API_OBJCALL_INT_POBJ_PBOOL(CLASS, METHOD, P1CLASS) \
511 	ASSERT_OBJ_PARAM_COUNT(METHOD, 2); \
512 	return RuntimeScriptValue().SetInt32(METHOD((CLASS*)self, (P1CLASS*)params[0].Ptr, params[1].GetAsBool()))
513 
514 #define API_OBJCALL_FLOAT(CLASS, METHOD) \
515 	ASSERT_SELF(METHOD); \
516 	return RuntimeScriptValue().SetFloat(METHOD((CLASS*)self))
517 
518 #define API_OBJCALL_BOOL(CLASS, METHOD) \
519 	ASSERT_SELF(METHOD); \
520 	return RuntimeScriptValue().SetInt32AsBool(METHOD((CLASS*)self))
521 
522 #define API_OBJCALL_BOOL_PINT(CLASS, METHOD) \
523 	ASSERT_OBJ_PARAM_COUNT(METHOD, 1); \
524 	return RuntimeScriptValue().SetInt32AsBool(METHOD((CLASS*)self, params[0].IValue))
525 
526 #define API_OBJCALL_BOOL_POBJ(CLASS, METHOD, P1CLASS) \
527 	ASSERT_OBJ_PARAM_COUNT(METHOD, 1); \
528 	return RuntimeScriptValue().SetInt32AsBool(METHOD((CLASS*)self, (P1CLASS*)params[0].Ptr))
529 
530 #define API_OBJCALL_BOOL_POBJ_PINT(CLASS, METHOD, P1CLASS) \
531 	ASSERT_OBJ_PARAM_COUNT(METHOD, 2); \
532 	return RuntimeScriptValue().SetInt32AsBool(METHOD((CLASS*)self, (P1CLASS*)params[0].Ptr, params[1].IValue))
533 
534 #define API_OBJCALL_BOOL_POBJ2(CLASS, METHOD, P1CLASS, P2CLASS) \
535 	ASSERT_OBJ_PARAM_COUNT(METHOD, 2); \
536 	return RuntimeScriptValue().SetInt32AsBool(METHOD((CLASS*)self, (P1CLASS*)params[0].Ptr, (P2CLASS*)params[1].Ptr))
537 
538 #define API_OBJCALL_BOOL(CLASS, METHOD) \
539 	ASSERT_SELF(METHOD); \
540 	return RuntimeScriptValue().SetInt32AsBool(METHOD((CLASS*)self))
541 
542 #define API_OBJCALL_OBJ_PINT_POBJ(CLASS, RET_CLASS, RET_MGR, METHOD, P1CLASS) \
543 	ASSERT_OBJ_PARAM_COUNT(METHOD, 2); \
544 	return RuntimeScriptValue().SetDynamicObject((void*)METHOD((CLASS*)self, params[0].IValue, (P1CLASS*)params[1].Ptr), &RET_MGR)
545 
546 #define API_OBJCALL_OBJ_POBJ2_PINT(CLASS, RET_CLASS, RET_MGR, METHOD, P1CLASS, P2CLASS) \
547 	ASSERT_OBJ_PARAM_COUNT(METHOD, 3); \
548 	return RuntimeScriptValue().SetDynamicObject((void*)METHOD((CLASS*)self, (P1CLASS*)params[0].Ptr, (P2CLASS*)params[1].Ptr, params[2].IValue), &RET_MGR)
549 
550 #define API_OBJCALL_OBJ_POBJ2_PBOOL(CLASS, RET_CLASS, RET_MGR, METHOD, P1CLASS, P2CLASS) \
551 	ASSERT_OBJ_PARAM_COUNT(METHOD, 3); \
552 	return RuntimeScriptValue().SetDynamicObject((void*)METHOD((CLASS*)self, (P1CLASS*)params[0].Ptr, (P2CLASS*)params[1].Ptr, params[2].GetAsBool()), &RET_MGR)
553 
554 #define API_CONST_OBJCALL_OBJ_POBJ2_PBOOL(CLASS, RET_CLASS, RET_MGR, METHOD, P1CLASS, P2CLASS) \
555 	ASSERT_OBJ_PARAM_COUNT(METHOD, 3); \
556 	return RuntimeScriptValue().SetDynamicObject(const_cast<void *>((const void *)METHOD((CLASS*)self, (P1CLASS*)params[0].Ptr, (P2CLASS*)params[1].Ptr, params[2].GetAsBool())), &RET_MGR)
557 
558 #define API_OBJCALL_OBJ(CLASS, RET_CLASS, RET_MGR, METHOD) \
559 	ASSERT_SELF(METHOD); \
560 	return RuntimeScriptValue().SetDynamicObject((void*)(RET_CLASS*)METHOD((CLASS*)self), &RET_MGR)
561 
562 #define API_CONST_OBJCALL_OBJ(CLASS, RET_CLASS, RET_MGR, METHOD) \
563 	ASSERT_SELF(METHOD); \
564 	return RuntimeScriptValue().SetDynamicObject(const_cast<void *>((const void *)(RET_CLASS*)METHOD((CLASS*)self)), &RET_MGR)
565 
566 #define API_OBJCALL_OBJ_PINT(CLASS, RET_CLASS, RET_MGR, METHOD) \
567 	ASSERT_OBJ_PARAM_COUNT(METHOD, 1); \
568 	return RuntimeScriptValue().SetDynamicObject((void*)(RET_CLASS*)METHOD((CLASS*)self, params[0].IValue), &RET_MGR)
569 
570 #define API_CONST_OBJCALL_OBJ_PINT(CLASS, RET_CLASS, RET_MGR, METHOD) \
571 	ASSERT_OBJ_PARAM_COUNT(METHOD, 1); \
572 	return RuntimeScriptValue().SetDynamicObject(const_cast<void *>((const void *)(RET_CLASS*)METHOD((CLASS*)self, params[0].IValue)), &RET_MGR)
573 
574 #define API_OBJCALL_OBJ_PINT2(CLASS, RET_CLASS, RET_MGR, METHOD) \
575 	ASSERT_OBJ_PARAM_COUNT(METHOD, 2); \
576 	return RuntimeScriptValue().SetDynamicObject((void*)(RET_CLASS*)METHOD((CLASS*)self, params[0].IValue, params[1].IValue), &RET_MGR)
577 
578 #define API_CONST_OBJCALL_OBJ_PINT2(CLASS, RET_CLASS, RET_MGR, METHOD) \
579 	ASSERT_OBJ_PARAM_COUNT(METHOD, 2); \
580 	return RuntimeScriptValue().SetDynamicObject(const_cast<void *>((const void *)(RET_CLASS*)METHOD((CLASS*)self, params[0].IValue, params[1].IValue)), &RET_MGR)
581 
582 #define API_OBJCALL_OBJ_PINT3(CLASS, RET_CLASS, RET_MGR, METHOD) \
583 	ASSERT_OBJ_PARAM_COUNT(METHOD, 3); \
584 	return RuntimeScriptValue().SetDynamicObject((void*)(RET_CLASS*)METHOD((CLASS*)self, params[0].IValue, params[1].IValue, params[2].IValue), &RET_MGR)
585 
586 #define API_OBJCALL_OBJ_POBJ(CLASS, RET_CLASS, RET_MGR, METHOD, P1CLASS) \
587 	ASSERT_OBJ_PARAM_COUNT(METHOD, 1); \
588 	return RuntimeScriptValue().SetDynamicObject((void*)(RET_CLASS*)METHOD((CLASS*)self, (P1CLASS*)params[0].Ptr), &RET_MGR)
589 
590 #define API_CONST_OBJCALL_OBJ_POBJ(CLASS, RET_CLASS, RET_MGR, METHOD, P1CLASS) \
591 	ASSERT_OBJ_PARAM_COUNT(METHOD, 1); \
592 	return RuntimeScriptValue().SetDynamicObject(const_cast<void *>((const void *)(RET_CLASS*)METHOD((CLASS*)self, (P1CLASS*)params[0].Ptr)), &RET_MGR)
593 
594 #define API_OBJCALL_OBJAUTO(CLASS, RET_CLASS, METHOD) \
595 	ASSERT_SELF(METHOD); \
596 	RET_CLASS* ret_obj = METHOD((CLASS*)self); \
597 	return RuntimeScriptValue().SetDynamicObject(ret_obj, ret_obj)
598 
599 #define API_OBJCALL_OBJAUTO_PINT2_PBOOL(CLASS, RET_CLASS, METHOD) \
600 	ASSERT_OBJ_PARAM_COUNT(METHOD, 3); \
601 	RET_CLASS* ret_obj = METHOD((CLASS*)self, params[0].IValue, params[1].IValue, params[2].GetAsBool()); \
602 	return RuntimeScriptValue().SetDynamicObject(ret_obj, ret_obj)
603 
604 #define API_OBJCALL_OBJAUTO_POBJ(CLASS, RET_CLASS, METHOD, P1CLASS) \
605 	ASSERT_OBJ_PARAM_COUNT(METHOD, 1); \
606 	RET_CLASS* ret_obj = METHOD((CLASS*)self, (P1CLASS*)params[0].Ptr); \
607 	return RuntimeScriptValue().SetDynamicObject(ret_obj, ret_obj)
608 
609 } // namespace AGS3
610 
611 #endif
612