1 /*
2 rua_script.c
3
4 Script api for ruamoko
5
6 Copyright (C) 2004 Bill Currie
7
8 Author: Bill Currie
9 Date: 2002/11/11
10
11 This program is free software; you can redistribute it and/or
12 modify it under the terms of the GNU General Public License
13 as published by the Free Software Foundation; either version 2
14 of the License, or (at your option) any later version.
15
16 This program is distributed in the hope that it will be useful,
17 but WITHOUT ANY WARRANTY; without even the implied warranty of
18 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
19
20 See the GNU General Public License for more details.
21
22 You should have received a copy of the GNU General Public License
23 along with this program; if not, write to:
24
25 Free Software Foundation, Inc.
26 59 Temple Place - Suite 330
27 Boston, MA 02111-1307, USA
28
29 */
30 #ifdef HAVE_CONFIG_H
31 # include "config.h"
32 #endif
33
34 #include <stdlib.h>
35 #ifdef HAVE_STRING_H
36 # include <string.h>
37 #endif
38 #ifdef HAVE_STRINGS_H
39 # include <strings.h>
40 #endif
41
42 #include "QF/progs.h"
43 #include "QF/script.h"
44
45 #include "rua_internal.h"
46
47 typedef struct {
48 script_t script;
49 string_t dstr;
50 progs_t *pr;
51 string_t err_msg;
52 } rua_script_t;
53
54 typedef struct {
55 PR_RESMAP(rua_script_t) scripts;
56 } script_resources_t;
57
58 static rua_script_t *
script_new(script_resources_t * res)59 script_new (script_resources_t *res)
60 {
61 PR_RESNEW (rua_script_t, res->scripts);
62 }
63
64 static void
script_free(script_resources_t * res,rua_script_t * script)65 script_free (script_resources_t *res, rua_script_t *script)
66 {
67 PR_RESFREE (rua_script_t, res->scripts, script);
68 }
69
70 static void
script_reset(script_resources_t * res)71 script_reset (script_resources_t *res)
72 {
73 PR_RESRESET (rua_script_t, res->scripts);
74 }
75
76 static inline rua_script_t *
script_get(script_resources_t * res,int index)77 script_get (script_resources_t *res, int index)
78 {
79 PR_RESGET(res->scripts, index);
80 }
81
82 static inline int
script_index(script_resources_t * res,rua_script_t * script)83 script_index (script_resources_t *res, rua_script_t *script)
84 {
85 PR_RESINDEX(res->scripts, script);
86 }
87
88 static void
bi_script_clear(progs_t * pr,void * data)89 bi_script_clear (progs_t *pr, void *data)
90 {
91 script_resources_t *res = (script_resources_t *) data;
92 script_reset (res);
93 }
94
95 static void
bi_script_error(script_t * _script,const char * msg)96 bi_script_error (script_t *_script, const char *msg)
97 {
98 rua_script_t *script = (rua_script_t *)_script;
99 script->err_msg = PR_SetString (script->pr, msg);
100 }
101
102 static void
bi_Script_New(progs_t * pr)103 bi_Script_New (progs_t *pr)
104 {
105 script_resources_t *res = PR_Resources_Find (pr, "Script");
106 rua_script_t *script = script_new (res);
107
108 if (!script)
109 PR_RunError (pr, "out of memory");
110
111 script->dstr = PR_NewMutableString (pr);
112 script->script.token = PR_GetMutableString (pr, script->dstr);
113 script->script.error = bi_script_error;
114 script->pr = pr;
115 R_INT (pr) = script_index (res, script);
116 }
117
118 static void
bi_Script_Delete(progs_t * pr)119 bi_Script_Delete (progs_t *pr)
120 {
121 script_resources_t *res = PR_Resources_Find (pr, "Script");
122 rua_script_t *script = script_get (res, P_INT (pr, 0));
123
124 if (!script)
125 PR_RunError (pr, "invalid script handle");
126 PR_FreeString (pr, script->dstr);
127 script_free (res, script);
128 }
129
130 static void
bi_Script_Start(progs_t * pr)131 bi_Script_Start (progs_t *pr)
132 {
133 script_resources_t *res = PR_Resources_Find (pr, "Script");
134 rua_script_t *script = script_get (res, P_INT (pr, 0));
135
136 if (!script)
137 PR_RunError (pr, "invalid script handle");
138 Script_Start (&script->script, P_GSTRING (pr, 1), P_GSTRING (pr, 2));
139 R_STRING (pr) = script->dstr;
140 }
141
142 static void
bi_Script_TokenAvailable(progs_t * pr)143 bi_Script_TokenAvailable (progs_t *pr)
144 {
145 script_resources_t *res = PR_Resources_Find (pr, "Script");
146 rua_script_t *script = script_get (res, P_INT (pr, 0));
147
148 if (!script)
149 PR_RunError (pr, "invalid script handle");
150 R_INT (pr) = Script_TokenAvailable (&script->script, P_INT (pr, 1));
151 }
152
153 static void
bi_Script_GetToken(progs_t * pr)154 bi_Script_GetToken (progs_t *pr)
155 {
156 script_resources_t *res = PR_Resources_Find (pr, "Script");
157 rua_script_t *script = script_get (res, P_INT (pr, 0));
158
159 if (!script)
160 PR_RunError (pr, "invalid script handle");
161 R_INT (pr) = Script_GetToken (&script->script, P_INT (pr, 1));
162 }
163
164 static void
bi_Script_UngetToken(progs_t * pr)165 bi_Script_UngetToken (progs_t *pr)
166 {
167 script_resources_t *res = PR_Resources_Find (pr, "Script");
168 rua_script_t *script = script_get (res, P_INT (pr, 0));
169
170 if (!script)
171 PR_RunError (pr, "invalid script handle");
172 Script_UngetToken (&script->script);
173 }
174
175 static void
bi_Script_Error(progs_t * pr)176 bi_Script_Error (progs_t *pr)
177 {
178 script_resources_t *res = PR_Resources_Find (pr, "Script");
179 rua_script_t *script = script_get (res, P_INT (pr, 0));
180
181 if (!script)
182 PR_RunError (pr, "invalid script handle");
183 R_STRING (pr) = script->err_msg;
184 script->err_msg = 0;
185 }
186
187 static void
bi_Script_NoQuoteLines(progs_t * pr)188 bi_Script_NoQuoteLines (progs_t *pr)
189 {
190 script_resources_t *res = PR_Resources_Find (pr, "Script");
191 rua_script_t *script = script_get (res, P_INT (pr, 0));
192
193 if (!script)
194 PR_RunError (pr, "invalid script handle");
195 R_INT (pr) = script->script.no_quote_lines;
196 script->script.no_quote_lines = P_INT (pr, 1);
197 }
198
199 static builtin_t builtins[] = {
200 {"Script_New", bi_Script_New, -1},
201 {"Script_Delete", bi_Script_Delete, -1},
202 {"Script_Start", bi_Script_Start, -1},
203 {"Script_TokenAvailable", bi_Script_TokenAvailable, -1},
204 {"Script_GetToken", bi_Script_GetToken, -1},
205 {"Script_UngetToken", bi_Script_UngetToken, -1},
206 {"Script_Error", bi_Script_Error, -1},
207 {"Script_NoQuoteLines", bi_Script_NoQuoteLines, -1},
208 {0}
209 };
210
211 void
RUA_Script_Init(progs_t * pr,int secure)212 RUA_Script_Init (progs_t *pr, int secure)
213 {
214 script_resources_t *res = calloc (1, sizeof (script_resources_t));
215
216 PR_Resources_Register (pr, "Script", res, bi_script_clear);
217
218 PR_RegisterBuiltins (pr, builtins);
219 }
220