e70e392df47a82e610059b207b6a9baaeec22c26
[supertux.git] / src / scripting / wrapper_util.cpp
1 #include <config.h>
2
3 #include <stdexcept>
4 #include <sstream>
5 #include "wrapper_util.hpp"
6
7 static void register_function(HSQUIRRELVM v, SQFUNCTION func, const char* name)
8 {
9     sq_pushstring(v, name, -1);
10     sq_newclosure(v, func, 0); //create a new function
11     if(sq_createslot(v, -3) < 0) {
12         std::stringstream msg;
13         msg << "Couldn't register function '" << name << "'";
14         throw SquirrelError(v, msg.str());
15     }
16 }
17
18 static void _register_functions(HSQUIRRELVM v, WrappedFunction* functions)
19 {
20     for(WrappedFunction* func = functions; func->name != 0; ++func) {
21         register_function(v, func->f, func->name);
22     }
23 }
24
25 static void register_class(HSQUIRRELVM v, WrappedClass* wclass)
26 {
27     sq_pushstring(v, wclass->name, -1);
28     sq_newclass(v, false);
29     _register_functions(v, wclass->functions);
30     _register_constants(v, wclass->int_consts);
31     _register_constants(v, wclass->float_consts);
32     _register_constants(v, wclass->string_consts);
33
34     if(sq_createslot(v, -3) < 0) {
35         std::stringstream msg;
36         msg << "Couldn't register function '" << wclass->name << "'";
37         throw SquirrelError(v, msg.str());
38     }
39 }
40
41 void register_functions(HSQUIRRELVM v, WrappedFunction* functions)
42 {
43     sq_pushroottable(v);
44     _register_functions(v, functions);
45     sq_pop(v, 1);
46 }
47
48 void register_classes(HSQUIRRELVM v, WrappedClass* classes)
49 {
50     sq_pushroottable(v);
51     for(WrappedClass* wclass = classes; wclass->name != 0; ++wclass) {
52         register_class(v, wclass);
53     }
54     sq_pop(v, 1);
55 }
56
57
58 void print_squirrel_stack(HSQUIRRELVM v)
59 {
60     printf("--------------------------------------------------------------\n");
61     int count = sq_gettop(v);
62     for(int i = 1; i <= count; ++i) {
63         printf("%d: ",i);
64         switch(sq_gettype(v, i))
65         {
66             case OT_NULL:
67                 printf("null");        
68                 break;
69             case OT_INTEGER: {
70                 int val;
71                 sq_getinteger(v, i, &val);
72                 printf("integer (%d)", val);
73                 break;
74             }
75             case OT_FLOAT: {
76                 float val;
77                 sq_getfloat(v, i, &val);
78                 printf("float (%f)", val);
79                 break;
80             }
81             case OT_STRING: {
82                 const char* val;
83                 sq_getstring(v, i, &val);
84                 printf("string (%s)", val);
85                 break;    
86             }
87             case OT_TABLE:
88                 printf("table");
89                 break;
90             case OT_ARRAY:
91                 printf("array");
92                 break;
93             case OT_USERDATA:
94                 printf("userdata");
95                 break;
96             case OT_CLOSURE:        
97                 printf("closure(function)");    
98                 break;
99             case OT_NATIVECLOSURE:
100                 printf("native closure(C function)");
101                 break;
102             case OT_GENERATOR:
103                 printf("generator");
104                 break;
105             case OT_USERPOINTER:
106                 printf("userpointer");
107                 break;
108             case OT_THREAD:
109                 printf("thread");
110                 break;
111             case OT_CLASS:
112                 printf("class");
113                 break;
114             case OT_INSTANCE:
115                 printf("instance");
116                 break;
117             default:
118                 printf("unknown?!?");
119                 break;
120         }
121         printf("\n");
122     }
123     printf("--------------------------------------------------------------\n");
124 }
125
126 //----------------------------------------------------------------------------
127
128 SquirrelError::SquirrelError(HSQUIRRELVM v, const std::string& message) throw()
129 {
130   std::ostringstream msg;
131   msg << "SQuirrel error: " << message << " (";
132   const char* lasterr;
133   sq_getlasterror(v);
134   if(sq_gettype(v, -1) != OT_STRING) {
135     lasterr = "no error info";
136   } else {
137     sq_getstring(v, -1, &lasterr);
138   }
139   sq_pop(v, 1);
140   msg << lasterr << ")";
141   this->message = msg.str();
142 }
143
144 SquirrelError::~SquirrelError() throw()
145 {}
146
147 const char*
148 SquirrelError::what() const throw()
149 {
150   return message.c_str();
151 }