1
2 #include "qcc.h"
3 #include "hash.h"
4
5 pr_info_t pr;
6 boolean pr_system;
7 def_t *pr_global_defs[MAX_REGS]; // to find def for a global variable
8 int pr_edict_size;
9 boolean expectint;
10
11 int shortened_store = 0;
12 char *typenames[] = {"void", "string", "float", "vector", "entity", "field", "function", "pointer", "int", "bad"};
13
14
15 //========================================
16
17 def_t *pr_scope; // the function being parsed, or NULL
18 boolean pr_dumpasm;
19 string_t s_file; // filename for function definition
20
21 int locals_end; // for tracking local variables vs temps
22
23 jmp_buf pr_parse_abort; // longjump with this on parse error
24
25 void PR_ParseDefs (void);
26 void PR_ParseState (void);
27
28 //========================================
29
30 opcode_t pr_opcodes[] =
31 {
32 {"<DONE>", OP2_DONE, -1, false, &def_entity, &def_field, &def_void},
33
34 {"*", OP2_MUL_F, 2, false, &def_float, &def_float, &def_float},
35 {"*", OP2_MUL_V, 2, false, &def_vector, &def_vector, &def_float},
36 {"*", OP2_MUL_FV, 2, false, &def_float, &def_vector, &def_vector},
37 {"*", OP2_MUL_VF, 2, false, &def_vector, &def_float, &def_vector},
38
39 {"/", OP2_DIV_F, 2, false, &def_float, &def_float, &def_float},
40
41 {"+", OP2_ADD_F, 3, false, &def_float, &def_float, &def_float},
42 {"+", OP2_ADD_V, 3, false, &def_vector, &def_vector, &def_vector},
43
44 {"-", OP2_SUB_F, 3, false, &def_float, &def_float, &def_float},
45 {"-", OP2_SUB_V, 3, false, &def_vector, &def_vector, &def_vector},
46
47 {"==", OP2_EQ_F, 4, false, &def_float, &def_float, &def_float},
48 {"==", OP2_EQ_V, 4, false, &def_vector, &def_vector, &def_float},
49 {"==", OP2_EQ_S, 4, false, &def_string, &def_string, &def_float},
50 {"==", OP2_EQ_E, 4, false, &def_entity, &def_entity, &def_float},
51 {"==", OP2_EQ_FNC, 4, false, &def_function, &def_function, &def_float},
52
53 {"!=", OP2_NE_F, 4, false, &def_float, &def_float, &def_float},
54 {"!=", OP2_NE_V, 4, false, &def_vector, &def_vector, &def_float},
55 {"!=", OP2_NE_S, 4, false, &def_string, &def_string, &def_float},
56 {"!=", OP2_NE_E, 4, false, &def_entity, &def_entity, &def_float},
57 {"!=", OP2_NE_FNC, 4, false, &def_function, &def_function, &def_float},
58
59 {"<=", OP2_LE, 4, false, &def_float, &def_float, &def_float},
60 {">=", OP2_GE, 4, false, &def_float, &def_float, &def_float},
61 {"<", OP2_LT, 4, false, &def_float, &def_float, &def_float},
62 {">", OP2_GT, 4, false, &def_float, &def_float, &def_float},
63
64 {".", OP2_LOAD_F, 1, false, &def_entity, &def_field, &def_float},
65 {".", OP2_LOAD_V, 1, false, &def_entity, &def_field, &def_vector},
66 {".", OP2_LOAD_S, 1, false, &def_entity, &def_field, &def_string},
67 {".", OP2_LOAD_ENT, 1, false, &def_entity, &def_field, &def_entity},
68 {".", OP2_LOAD_FLD, 1, false, &def_entity, &def_field, &def_field},
69 {".", OP2_LOAD_FNC, 1, false, &def_entity, &def_field, &def_function},
70
71 {".", OP2_ADDRESS, 1, false, &def_entity, &def_field, &def_pointer},
72
73 {"=", OP2_STORE_F, 5, true, &def_float, &def_float, &def_float},
74 {"=", OP2_STORE_V, 5, true, &def_vector, &def_vector, &def_vector},
75 {"=", OP2_STORE_S, 5, true, &def_string, &def_string, &def_string},
76 {"=", OP2_STORE_ENT, 5, true, &def_entity, &def_entity, &def_entity},
77 {"=", OP2_STORE_FLD, 5, true, &def_field, &def_field, &def_field},
78 {"=", OP2_STORE_FNC, 5, true, &def_function, &def_function, &def_function},
79
80 {"=", OP2_STOREP_F, 5, true, &def_pointer, &def_float, &def_float},
81 {"=", OP2_STOREP_V, 5, true, &def_pointer, &def_vector, &def_vector},
82 {"=", OP2_STOREP_S, 5, true, &def_pointer, &def_string, &def_string},
83 {"=", OP2_STOREP_ENT, 5, true, &def_pointer, &def_entity, &def_entity},
84 {"=", OP2_STOREP_FLD, 5, true, &def_pointer, &def_field, &def_field},
85 {"=", OP2_STOREP_FNC, 5, true, &def_pointer, &def_function, &def_function},
86
87 {"<RETURN>", OP2_RETURN, -1, false, &def_void, &def_void, &def_void},
88
89 {"!", OP2_NOT_F, -1, false, &def_float, &def_void, &def_float},
90 {"!", OP2_NOT_V, -1, false, &def_vector, &def_void, &def_float},
91 {"!", OP2_NOT_S, -1, false, &def_vector, &def_void, &def_float},
92 {"!", OP2_NOT_ENT, -1, false, &def_entity, &def_void, &def_float},
93 {"!", OP2_NOT_FNC, -1, false, &def_function, &def_void, &def_float},
94
95 {"<IF>", OP2_IF, -1, false, &def_float, &def_float, &def_void},
96 {"<IFNOT>", OP2_IFNOT, -1, false, &def_float, &def_float, &def_void},
97
98 {"<STATE>", OP2_STATE, -1, false, &def_float, &def_float, &def_void},
99
100 {"<GOTO>", OP2_GOTO, -1, false, &def_float, &def_void, &def_void},
101 // extra conditional crap FrikaC
102 // I must be nuts :)
103 {"&&", OP2_AND, 6, false, &def_float, &def_float, &def_float},
104 {"&&", OP2_AND, 6, false, &def_entity, &def_float, &def_float},
105 {"&&", OP2_AND, 6, false, &def_float, &def_entity, &def_float},
106 {"&&", OP2_AND, 6, false, &def_entity, &def_entity, &def_float},
107
108 {"||", OP2_OR, 6, false, &def_float, &def_float, &def_float},
109 {"||", OP2_OR, 6, false, &def_entity, &def_float, &def_float},
110 {"||", OP2_OR, 6, false, &def_float, &def_entity, &def_float},
111 {"||", OP2_OR, 6, false, &def_entity, &def_entity, &def_float},
112
113 {"&", OP2_BITAND, 2, false, &def_float, &def_float, &def_float},
114
115 {"|", OP2_BITOR, 2, false, &def_float, &def_float, &def_float},
116
117 {"[", OP2_LOAD_F, 1, false, &def_void, &def_float, &def_float},
118 {"[", OP2_LOAD_F, 1, false, &def_entity, &def_float, &def_float},
119 {"[", OP2_LOAD_S, 1, false, &def_void, &def_float, &def_string},
120 {"[", OP2_LOAD_ENT, 1, false, &def_void, &def_float, &def_entity},
121 {"[", OP2_ADD_F, 1, false, &def_string, &def_float, &def_string},
122 {"[", OP2_LOAD_V, 1, false, &def_void, &def_float, &def_vector},
123 {"[", OP2_LOAD_FLD, 1, false, &def_void, &def_float, &def_field},
124 {"[", OP2_LOAD_FNC, 1, false, &def_void, &def_float, &def_function},
125
126 {"+=", OP_ADD_F, 5, true, &def_float, &def_float, &def_float},
127 {"+=", OP_ADD_V, 5, true, &def_vector, &def_vector, &def_vector},
128 {"+=", OP_ADD_F, 5, true, &def_pointer, &def_float, &def_float},
129 {"+=", OP_ADD_V, 5, true, &def_pointer, &def_vector, &def_vector},
130 {"-=", OP_SUB_F, 5, true, &def_float, &def_float, &def_float},
131 {"-=", OP_SUB_V, 5, true, &def_vector, &def_vector, &def_vector},
132 {"-=", OP_SUB_F, 5, true, &def_pointer, &def_float, &def_float},
133 {"-=", OP_SUB_V, 5, true, &def_pointer, &def_vector, &def_vector},
134
135 {"*=", OP_MUL_F, 5, true, &def_float, &def_float, &def_float},
136 {"*=", OP_MUL_F, 5, true, &def_pointer, &def_float, &def_float},
137
138 {"/=", OP_DIV_F, 5, true, &def_float, &def_float, &def_float},
139 {"/=", OP_DIV_F, 5, true, &def_pointer, &def_float, &def_float},
140 {"&=", OP_BITAND, 5, true, &def_float, &def_float, &def_float},
141 {"&=", OP_BITAND, 5, true, &def_pointer, &def_float, &def_float},
142 {"|=", OP_BITOR, 5, true, &def_float, &def_float, &def_float},
143 {"|=", OP_BITOR, 5, true, &def_pointer, &def_float, &def_float},
144
145 {"++", OP2_ADD_F, 1, false, &def_float, &def_float, &def_float},
146 {"--", OP2_SUB_F, 1, false, &def_float, &def_float, &def_float},
147
148 {NULL}
149 };
150
151
152 char *opnames[] =
153 {
154 "<DONE>", "MUL_F", "MUL_V", "MUL_FV", "MUL_VF", "DIV_F", "ADD_F", "ADD_V", "SUB_F",
155 "SUB_V", "EQ_F", "EQ_V", "EQ_S", "EQ_E", "EQ_FNC", "NE_F", "NE_V", "NE_S", "NE_F",
156 "NE_FNC", "LE", "GE", "LT", "GT", "LOAD_F", "LOAD_V", "LOAD_S", "LOAD_ENT", "LOAD_FLD",
157 "LOAD_FNC",
158 "ADDRESS", "STORE_F", "STORE_V", "STORE_S", "STORE_ENT", "STORE_FLD", "STORE_FNC",
159 "STOREP_F", "STOREP_V", "STOREP_S", "STOREP_ENT", "STOREP_FLD", "STOREP_FUNC", "RETURN",
160 "NOT_F", "NOT_V", "NOT_S", "NOT_ENT", "NOT_FNC", "IF", "IFNOT", "CALL0", "CALL1", "CALL2",
161 "CALL3", "CALL4", "CALL5", "CALL6", "CALL7", "CALL8", "STATE", "GOTO", "AND", "OR",
162 "BITAND", "BITOR"
163 };
164
165 #define TOP_PRIORITY 6
166 #define NOT_PRIORITY 4
167
168 def_t *PR_Expression (int priority, boolean returnused);
169 //===========================================================================
170
171
PR_GetType(def_t * def)172 etype_t PR_GetType (def_t *def)
173 {
174 etype_t type = def->type->type;
175
176 if (def->cast)
177 {
178 type = def->cast;
179 def->cast = ev_void;
180 }
181 return type;
182 }
183
184 unsigned char used_temps[MAX_REGS];
185
GimmeATempFoo(int size)186 def_t *GimmeATempFoo (int size)
187 {
188 def_t *d;
189
190 if (!pr_scope)
191 PR_ParseError("WTF?! This should be impossible");
192 //veri tas
193 if (pr_optimize_recycle)
194 {
195 d = pr_scope->tempnext;
196
197 while (d)
198 {
199 if (!used_temps[d->ofs])
200 {
201 if (type_size[d->type->type] == size)
202 {
203 num_recycled += size;
204 return d;
205 }
206 }
207 d = d->tempnext;
208 }
209 }
210
211 d = (struct def_s *) PR_Malloc (sizeof(def_t));
212 d->ofs = numpr_globals;
213 d->tempnext = pr_scope->tempnext;
214 pr_scope->tempnext = d;
215 if (pr_optimize_recycle)
216 locals_end = numpr_globals; // bad
217 pr_global_defs[numpr_globals] = d;
218 numpr_globals += size;
219 return d;
220 }
221
222 def_t *PR_ParseImmediate (void);
ConstantArithmetic(opcode_t * op,def_t * var_a,def_t * var_b)223 def_t *ConstantArithmetic (opcode_t *op, def_t *var_a, def_t *var_b)
224 {
225 def_t *d;
226 switch(op->op)
227 {
228 case OP2_ADD_F:
229 if (var_a->constant && var_b->constant)
230 {
231 pr_immediate_type = &type_float;
232 pr_immediate._float = G_FLOAT(var_a->ofs) + G_FLOAT(var_b->ofs);
233 d = PR_ParseImmediate();
234 HashImmediate();
235 return d;
236 }
237 break;
238 case OP2_SUB_F:
239 if (var_a->constant && var_b->constant)
240 {
241 pr_immediate_type = &type_float;
242 pr_immediate._float = G_FLOAT(var_a->ofs) - G_FLOAT(var_b->ofs);
243 d = PR_ParseImmediate();
244 HashImmediate();
245 return d;
246 }
247 break;
248 case OP2_SUB_V:
249 if (var_a->constant && var_b->constant)
250 {
251 pr_immediate_type = &type_vector;
252 pr_immediate.vector[0] = G_VECTOR(var_a->ofs, 0) - G_VECTOR(var_b->ofs, 0);
253 pr_immediate.vector[1] = G_VECTOR(var_a->ofs, 1) - G_VECTOR(var_b->ofs, 1);
254 pr_immediate.vector[2] = G_VECTOR(var_a->ofs, 2) - G_VECTOR(var_b->ofs, 2);
255 d = PR_ParseImmediate();
256 HashImmediate();
257 return d;
258 }
259 break;
260 case OP2_ADD_V:
261 if (var_a->constant && var_b->constant)
262 {
263 pr_immediate_type = &type_vector;
264 pr_immediate.vector[0] = G_VECTOR(var_a->ofs, 0) + G_VECTOR(var_b->ofs, 0);
265 pr_immediate.vector[1] = G_VECTOR(var_a->ofs, 1) + G_VECTOR(var_b->ofs, 1);
266 pr_immediate.vector[2] = G_VECTOR(var_a->ofs, 2) + G_VECTOR(var_b->ofs, 2);
267 d = PR_ParseImmediate();
268 HashImmediate();
269 return d;
270 }
271 break;
272 case OP2_MUL_F:
273 if (var_a->constant && var_b->constant)
274 {
275 pr_immediate_type = &type_float;
276 pr_immediate._float = G_FLOAT(var_a->ofs) * G_FLOAT(var_b->ofs);
277 d = PR_ParseImmediate();
278 HashImmediate();
279 return d;
280 }
281 break;
282 case OP2_MUL_V:
283 if (var_a->constant && var_b->constant)
284 {
285 pr_immediate_type = &type_float;
286
287 pr_immediate._float = G_VECTOR(var_a->ofs, 0) * G_VECTOR(var_b->ofs, 0)+
288 G_VECTOR(var_a->ofs, 1) * G_VECTOR(var_b->ofs, 1) +
289 G_VECTOR(var_a->ofs, 2) * G_VECTOR(var_b->ofs, 2);
290 d = PR_ParseImmediate();
291 HashImmediate();
292 return d;
293 }
294 break;
295
296 case OP2_MUL_FV:
297 if (var_a->constant && var_b->constant)
298 {
299 pr_immediate_type = &type_vector;
300 pr_immediate.vector[0] = G_FLOAT(var_a->ofs) * G_VECTOR(var_b->ofs, 0);
301 pr_immediate.vector[1] = G_FLOAT(var_a->ofs) * G_VECTOR(var_b->ofs, 1);
302 pr_immediate.vector[2] = G_FLOAT(var_a->ofs) * G_VECTOR(var_b->ofs, 2);
303 d = PR_ParseImmediate();
304 HashImmediate();
305 return d;
306 }
307 break;
308
309 case OP2_MUL_VF:
310 if (var_a->constant && var_b->constant)
311 {
312 pr_immediate_type = &type_vector;
313 pr_immediate.vector[0] = G_FLOAT(var_b->ofs) * G_VECTOR(var_a->ofs, 0);
314 pr_immediate.vector[1] = G_FLOAT(var_b->ofs) * G_VECTOR(var_a->ofs, 1);
315 pr_immediate.vector[2] = G_FLOAT(var_b->ofs) * G_VECTOR(var_a->ofs, 2);
316 d = PR_ParseImmediate();
317 HashImmediate();
318 return d;
319 }
320
321 break;
322 case OP2_DIV_F:
323 if (var_a->constant && var_b->constant)
324 {
325 pr_immediate_type = &type_float;
326 pr_immediate._float = G_FLOAT(var_a->ofs) / G_FLOAT(var_b->ofs);
327 d = PR_ParseImmediate();
328 HashImmediate();
329 return d;
330 }
331 break;
332 case OP2_BITAND:
333 if (var_a->constant && var_b->constant)
334 {
335 pr_immediate_type = &type_float;
336 pr_immediate._float = G_INT(var_a->ofs) & G_INT(var_b->ofs);
337 d = PR_ParseImmediate();
338 HashImmediate();
339 return d;
340 }
341 break;
342 case OP2_BITOR:
343 if (var_a->constant && var_b->constant)
344 {
345 pr_immediate_type = &type_float;
346 pr_immediate._float = (int)G_FLOAT(var_a->ofs) | (int)G_FLOAT(var_b->ofs);
347 d = PR_ParseImmediate();
348 HashImmediate();
349 return d;
350 }
351 break;
352 case OP2_GE:
353 if (var_a->constant && var_b->constant)
354 {
355 pr_immediate_type = &type_float;
356 pr_immediate._float = G_FLOAT(var_a->ofs) >= G_FLOAT(var_b->ofs);
357 d = PR_ParseImmediate();
358 HashImmediate();
359 return d;
360 }
361 break;
362 case OP2_LE:
363 if (var_a->constant && var_b->constant)
364 {
365 pr_immediate_type = &type_float;
366 pr_immediate._float = G_FLOAT(var_a->ofs) <= G_FLOAT(var_b->ofs);
367 d = PR_ParseImmediate();
368 HashImmediate();
369 return d;
370 }
371 break;
372 case OP2_LT:
373 if (var_a->constant && var_b->constant)
374 {
375 pr_immediate_type = &type_float;
376 pr_immediate._float = G_FLOAT(var_a->ofs) < G_FLOAT(var_b->ofs);
377 d = PR_ParseImmediate();
378 HashImmediate();
379 return d;
380 }
381 break;
382 case OP2_GT:
383 if (var_a->constant && var_b->constant)
384 {
385 pr_immediate_type = &type_float;
386 pr_immediate._float = G_FLOAT(var_a->ofs) > G_FLOAT(var_b->ofs);
387 d = PR_ParseImmediate();
388 HashImmediate();
389 return d;
390 }
391 break;
392 case OP2_OR:
393 if (var_a->constant && var_b->constant)
394 {
395 pr_immediate_type = &type_float;
396 pr_immediate._float = G_FLOAT(var_a->ofs) || G_FLOAT(var_b->ofs);
397 d = PR_ParseImmediate();
398 HashImmediate();
399 return d;
400 }
401 break;
402 case OP2_AND:
403 if (var_a->constant && var_b->constant)
404 {
405 pr_immediate_type = &type_float;
406 pr_immediate._float = G_FLOAT(var_a->ofs) && G_FLOAT(var_b->ofs);
407 d = PR_ParseImmediate();
408 HashImmediate();
409 return d;
410 }
411 break;
412 case OP2_NOT_F:
413 if (var_a->constant)
414 {
415 pr_immediate_type = &type_float;
416 pr_immediate._float = !G_FLOAT(var_a->ofs);
417 d = PR_ParseImmediate();
418 HashImmediate();
419 return d;
420 }
421 break;
422 case OP2_NOT_V:
423 if (var_a->constant)
424 {
425 pr_immediate_type = &type_float;
426 pr_immediate._float = !G_VECTOR(var_a->ofs, 0) && !G_VECTOR(var_a->ofs, 1) && !G_VECTOR(var_a->ofs, 2);
427 d = PR_ParseImmediate();
428 HashImmediate();
429 return d;
430 }
431 break;
432 case OP_EQ_F:
433 if (var_a->constant && var_b->constant)
434 {
435 pr_immediate_type = &type_float;
436 pr_immediate._float = G_FLOAT(var_a->ofs) == G_FLOAT(var_b->ofs);
437 d = PR_ParseImmediate();
438 HashImmediate();
439 return d;
440 }
441 break;
442 case OP_NE_F:
443 if (var_a->constant && var_b->constant)
444 {
445 pr_immediate_type = &type_float;
446 pr_immediate._float = G_FLOAT(var_a->ofs) != G_FLOAT(var_b->ofs);
447 d = PR_ParseImmediate();
448 HashImmediate();
449 return d;
450 }
451 break;
452 }
453 return NULL;
454 }
455
456
457 /*
458 ============
459 PR_Statement
460
461 Emits a primitive statement, returning the var it places it's value in
462 ============
463 */
SimpleStatement(int op,int var_a,int var_b,int var_c)464 dstatement_t *SimpleStatement( int op, int var_a, int var_b, int var_c)
465 {
466 dstatement_t *statement;
467
468 statement_linenums[numstatements] = pr_source_line;
469 statement = &statements[numstatements];
470
471 numstatements++;
472 statement->op = op;
473 statement->a = var_a;
474 statement->b = var_b;
475 statement->c = var_c;
476 return statement;
477 }
478
PR_Statement(opcode_t * op,def_t * var_a,def_t * var_b)479 def_t *PR_Statement ( opcode_t *op, def_t *var_a, def_t *var_b)
480 {
481 dstatement_t *statement, *sprev;
482 def_t *var_c;
483 boolean templast;
484
485 if (var_a)
486 if (var_a->ofs >= 0)
487 used_temps[var_a->ofs] = 0;
488 if (var_b)
489 if (var_b->ofs >= 0)
490 used_temps[var_b->ofs] = 0;
491
492 templast = false;
493
494 if (numstatements)
495 {
496 sprev = &statements[numstatements - 1];
497 if (sprev->c)
498 if (!pr_global_defs[sprev->c]->name)
499 templast = true;
500 }
501 if (pr_optimize_constant_arithmetic)
502 {
503 var_c = ConstantArithmetic(op, var_a, var_b);
504 if (var_c)
505 {
506 num_constant_ops_saved++;
507 return var_c;
508 }
509 if (sprev->op == op->op)
510 {
511 var_c = pr_global_defs[sprev->b];
512 if (var_a && var_b && var_c)
513 {
514 if (var_b->constant && var_c->constant)
515 {
516 if (sprev->c == var_a->ofs && !var_a->name)
517 {
518 var_c = ConstantArithmetic(op, var_c, var_b);
519 if (var_c)
520 {
521 sprev->b = var_c->ofs;
522 num_constant_ops_saved++;
523 return pr_global_defs[sprev->c];
524 }
525 }
526 }
527 }
528 }
529 }
530
531 statement = SimpleStatement(op->op, var_a ? var_a->ofs : 0, var_b ? var_b->ofs : 0, 0);
532 shortened_store = 0;
533
534 if (op->type_c == &def_void || op->right_associative)
535 {
536 var_c = NULL;
537 statement->c = 0; // ifs, gotos, and assignments
538 // don't need vars allocated
539
540 if (templast)
541 {
542 if (pr_optimize_eliminate_temps && ((unsigned) (statement->op - OP2_STORE_F) < 6) && (statement->a == sprev->c))
543 {
544 sprev->c = statement->b;
545 numstatements--;
546 num_stores_shortened++;
547 shortened_store = 1;
548 return var_b;
549 }
550 else if (pr_optimize_shorten_ifs && (statement->op == OP2_IFNOT))
551 {
552 if (sprev->op == OP2_NOT_F || sprev->op == OP2_NOT_FNC || sprev->op == OP2_NOT_ENT)
553 {
554 sprev->op = OP2_IF;
555 numstatements--;
556 num_ifs_shortened++;
557 }
558 }
559 else if (pr_optimize_shorten_ifs && (statement->op == OP2_IF))
560 {
561 if (sprev->op == OP2_NOT_F || sprev->op == OP2_NOT_FNC || sprev->op == OP2_NOT_ENT)
562 {
563 sprev->op = OP2_IFNOT;
564 numstatements--;
565 num_ifs_shortened++;
566 }
567 }
568 }
569 }
570 else
571 { // allocate result space
572 var_c = GimmeATempFoo(type_size[op->type_c->type->type]);;
573 var_c->type = op->type_c->type;
574 var_c->cast = ev_void;
575 statement->c = var_c->ofs;
576
577 if (var_c)
578 used_temps[var_c->ofs] = 1;
579 }
580
581
582 if (op->right_associative)
583 return var_a;
584 return var_c;
585 }
586
587 /*
588 ============
589 PR_GetImmediate
590
591 Looks for a preexisting constant; return NULL if none exists
592 ============
593 */
PR_GetImmediate(void)594 def_t *PR_GetImmediate (void)
595 {
596 def_t *cn = NULL;
597 struct hash_element *cell = NULL;
598
599 for (cell = htable[pr_immediate_index]; cell != NULL; cell = cell->next)
600 {
601 cn = cell->def;
602 if (!cn->constant || (cn->type != pr_immediate_type))
603 continue;
604 if (pr_immediate_type == &type_string)
605 {
606 if (memcmp(G_STRING(cn->ofs), pr_immediate_string, pr_immediate_strlen))
607 continue;
608 }
609 else if (pr_immediate_type == &type_vector)
610 {
611 if ((G_FLOAT(cn->ofs) != pr_immediate.vector[0]) || (G_FLOAT(cn->ofs+1) != pr_immediate.vector[1]) || (G_FLOAT(cn->ofs+2) != pr_immediate.vector[2]))
612 continue;
613 }
614 else
615 {
616 if (G_INT(cn->ofs) != pr_immediate._int)
617 continue;
618 }
619
620 return cn;
621 }
622 return NULL;
623 }
624
625 /*
626 ============
627 PR_ParseImmediate
628
629 Looks for a preexisting constant; allocates a new one if none is found
630 ============
631 */
PR_ParseImmediate(void)632 def_t *PR_ParseImmediate (void)
633 {
634 def_t *cn = NULL;
635 struct hash_element *cell = NULL;
636
637 if (cn = PR_GetImmediate())
638 {
639 return cn;
640 }
641
642 // allocate a new one
643 cn = (struct def_s *) PR_Malloc (sizeof(def_t));
644
645 cn->next = NULL;
646 pr.def_tail->next = cn;
647 pr.def_tail = cn;
648
649 cell = (struct hash_element *) PR_Malloc (sizeof(struct hash_element));
650 cell->next = htable[pr_immediate_index];
651 cell->def = cn;
652 htable[pr_immediate_index] = cell;
653 stats[pr_immediate_index]++;
654
655 cn->type = pr_immediate_type;
656 cn->name = "IMMEDIATE";
657 cn->constant = 1;
658 cn->defined = 1;
659 cn->save = 0;
660 cn->scope = NULL; // always share immediates
661 cn->cast = ev_void;
662
663 // copy the immediate to the global area
664 cn->ofs = numpr_globals;
665 pr_global_defs[cn->ofs] = cn;
666 numpr_globals += type_size[pr_immediate_type->type];
667 if (pr_immediate_type == &type_string)
668 pr_immediate.string = CopyString (pr_immediate_string, pr_immediate_strlen);
669
670 memcpy (pr_globals + cn->ofs, &pr_immediate, 4*type_size[pr_immediate_type->type]);
671
672 return cn;
673 }
674
PrecacheSound(def_t * e,int ch)675 void PrecacheSound (def_t *e, int ch)
676 {
677 char *n;
678 int i;
679
680 if (!e->ofs)
681 return;
682 n = G_STRING(e->ofs);
683 for (i=0 ; i<numsounds ; i++)
684 if (!STRCMP(n, precache_sounds[i]))
685 return;
686 if (numsounds == MAX_SOUNDS)
687 Sys_Error("PrecacheSound: numsounds == MAX_SOUNDS");
688 strcpy (precache_sounds[i], n);
689 if (ch >= '1' && ch <= '9')
690 precache_sounds_block[i] = ch - '0';
691 else
692 precache_sounds_block[i] = 1;
693 numsounds++;
694 }
695
PrecacheModel(def_t * e,int ch)696 void PrecacheModel (def_t *e, int ch)
697 {
698 char *n;
699 int i;
700
701 if (!e->ofs)
702 return;
703 n = G_STRING(e->ofs);
704 for (i=0 ; i<nummodels ; i++)
705 if (!STRCMP(n, precache_models[i]))
706 return;
707 if (numsounds == MAX_SOUNDS)
708 Sys_Error("PrecacheModels: numsounds == MAX_SOUNDS");
709 strcpy (precache_models[i], n);
710 if (ch >= '1' && ch <= '9')
711 precache_models_block[i] = ch - '0';
712 else
713 precache_models_block[i] = 1;
714 nummodels++;
715 }
716
PrecacheFile(def_t * e,int ch)717 void PrecacheFile (def_t *e, int ch)
718 {
719 char *n;
720 int i;
721
722 if (!e->ofs)
723 return;
724 n = G_STRING(e->ofs);
725 for (i=0 ; i<numfiles ; i++)
726 if (!STRCMP(n, precache_files[i]))
727 return;
728 if (numfiles == MAX_FILES)
729 Sys_Error("PrecacheFile: numfiles == MAX_FILES");
730 strcpy (precache_files[i], n);
731 if (ch >= '1' && ch <= '9')
732 precache_files_block[i] = ch - '0';
733 else
734 precache_files_block[i] = 1;
735 numfiles++;
736 }
737
738 /*
739 ============
740 PR_ParseFunctionCall
741 ============
742 */
743
744 // more than 8 parms keyword - locutus
745 def_t *extra_parms[MAX_EXTRA_PARMS];
746
747 def_t *ecorrection;
748
PR_ParseFunctionCall(def_t * func)749 def_t *PR_ParseFunctionCall (def_t *func)
750 {
751 def_t *e, *e2;
752 int arg, numtypes, i, returnused = 0;
753 type_t *t;
754 def_t *parms[MAX_PARMS + MAX_EXTRA_PARMS];
755
756 t = func->type;
757
758 if (t->type != ev_function)
759 PR_ParseError ("%s is not a function", t->def->name);
760
761 // copy the arguments to the global parameter variables
762 arg = 0;
763 numtypes = t->num_parms >= 0 ? t->num_parms : -1 - t->num_parms;
764 if (!PR_Check(")"))
765 {
766 do
767 {
768 if (t->num_parms >= 0 && arg >= t->num_parms)
769 {
770 if (func->name)
771 PR_ParseWarning (1, "%s: too many parameters, see definition %s(%i)", func->name, func->s_file, func->line);
772 else
773 PR_ParseWarning (1, "Indirect function: too many parameters");
774
775 }
776 if (t->num_parms < 0 && arg > MAX_PARMS)
777 PR_ParseWarning (1, "%s: vararg func cannot have more than %i parms", func->name, MAX_PARMS);
778
779 if (!PR_Check("#"))
780 {
781 if (t->parm_types[arg])
782 expectint = t->parm_types[arg]->type == ev_int;
783 e = PR_Expression (TOP_PRIORITY, returnused);
784 if (ecorrection)
785 {
786 parms[returnused] = ecorrection;
787 ecorrection = NULL;
788 }
789 if (e->ofs == OFS_RETURN)
790 returnused = arg;
791
792 if (arg == 0 && func->name)
793 {
794 // save information for model and sound caching
795 if (!strncmp(func->name,"precache_sound", 14))
796 PrecacheSound (e, func->name[14]);
797 else if (!strncmp(func->name,"precache_model", 14))
798 PrecacheModel (e, func->name[14]);
799 else if (!strncmp(func->name,"precache_file", 13))
800 PrecacheFile (e, func->name[13]);
801 }
802 if (e->cast)
803 {
804 if ((arg < numtypes) && ( e->cast != t->parm_types[arg]->type ) )
805 {
806 PR_ParseWarning (1, "%s: type mismatch on parm %i. Expected %s, found %s. See definition %s(%i)",
807 func->name, arg, typenames[t->parm_types[arg]->type], typenames[e->cast], func->s_file, func->line);
808 }
809 e->cast = ev_void;
810 }
811 else if ((arg < numtypes) && ( e->type != t->parm_types[arg] ) )
812 {
813 PR_ParseWarning (1, "%s: type mismatch on parm %i. Expected %s, found %s. See definition %s(%i)",
814 func->name, arg, typenames[t->parm_types[arg]->type], typenames[e->type->type], func->s_file, func->line);
815 }
816 // a vector copy will copy everything
817 parms[arg] = e;
818 if (arg < MAX_PARMS)
819 def_parms[arg].type = t->parm_types[arg];
820 else
821 {
822 if (!extra_parms[arg - MAX_PARMS])
823 {
824 e2 = (struct def_s *) PR_Malloc (sizeof(def_t));
825 e2->ofs = numpr_globals;
826 e2->name = "extra parm";
827 pr_global_defs[numpr_globals] = e2;
828 numpr_globals += 3;
829 extra_parms[arg - MAX_PARMS] = e2;
830 }
831 }
832 }
833 else
834 parms[arg] = NULL;
835 arg++;
836 }
837 while (PR_Check (","));
838
839 PR_Expect (")");
840 }
841 // FrikaC store all the parms *NOW*
842 if (arg > (MAX_PARMS + MAX_EXTRA_PARMS))
843 PR_ParseError ("%s: more than %i parameters illegal", func->name, MAX_PARMS + MAX_EXTRA_PARMS);
844 for (i = 0; i < arg; i++)
845 {
846 if (!parms[i])
847 continue;
848 if (i < MAX_PARMS)
849 {
850 if (pr_optimize_nonvec_parms && t->parm_types[i] != &type_vector)
851 {
852 PR_Statement (&pr_opcodes[OP_STORE_F], parms[i], &def_parms[i]);
853 num_nonvec_parms++;
854 }
855 else
856 PR_Statement (&pr_opcodes[OP_STORE_V], parms[i], &def_parms[i]);
857 }
858 else
859 {
860 if (!extra_parms[i - MAX_PARMS])
861 {
862 e2 = (struct def_s *) PR_Malloc (sizeof(def_t));
863 e2->ofs = numpr_globals;
864 e2->name = "extra parm";
865 pr_global_defs[numpr_globals] = e2;
866 numpr_globals += 3;
867 extra_parms[i - MAX_PARMS] = e2;
868 }
869 if (t->parm_types[i] != &type_vector)
870 PR_Statement (&pr_opcodes[OP_STORE_F], parms[i], extra_parms[i - MAX_PARMS]);
871 else
872 PR_Statement (&pr_opcodes[OP_STORE_V], parms[i], extra_parms[i - MAX_PARMS]);
873 }
874 }
875 if (arg < numtypes)
876 PR_ParseWarning (1, "%s: Too few parameters. See definition %s(%i)", func->name, func->s_file, func->line);
877
878 SimpleStatement (OP2_CALL0+ (arg > MAX_PARMS ? MAX_PARMS : arg), func->ofs, 0, 0);
879 def_ret.type = t->aux_type;
880 return &def_ret;
881 }
882
883 /*
884 ============
885 PR_ParseValue
886
887 Returns the global ofs for the current token
888 ============
889 */
PR_ParseValue(void)890 def_t *PR_ParseValue (void)
891 {
892 def_t *d;
893 char *name;
894
895 // if the token is an immediate, allocate a constant for it
896 if (pr_token_type == tt_immediate)
897 {
898 d = PR_ParseImmediate ();
899 PR_Lex();
900 return d;
901 }
902
903 name = PR_ParseName ();
904
905 // look through the defs
906 d = PR_GetDef (NULL, name, pr_scope, false, 0, 0);
907 if (!d)
908 PR_ParseError ("Unknown value \"%s\"", name);
909 return d;
910 }
911
912 /*
913 ============
914 PR_Cast
915 ============
916 */
PR_Cast(def_t * e,type_t * type)917 def_t *PR_Cast (def_t *e, type_t *type)
918 {
919 def_t *cast;
920
921 cast = (struct def_s *) PR_Malloc (sizeof(def_t));
922 memcpy (cast, e, sizeof(def_t));
923 cast->type = type;
924 return cast;
925 }
926
927 /*
928 ============
929 PR_Term
930 ============
931 */
PR_Term(void)932 def_t *PR_Term (void)
933 {
934 def_t *e, *e2;
935 etype_t t;
936 type_t *ty;
937
938 if (pr_token_type == tt_punct)
939 {
940 if (PR_Check("++"))
941 {
942
943 e = PR_Expression (1, false);
944 t = PR_GetType(e);
945 if (t == ev_int)
946 {
947 pr_immediate_type = &type_int;
948 pr_immediate._int = 1;
949 }
950 else
951 {
952 pr_immediate_type = &type_float;
953 pr_immediate._float = 1;
954 }
955 e2 = PR_ParseImmediate();
956 HashImmediate();
957 if (t != ev_float && t != ev_int)
958 PR_ParseError("Type mismatch for ++, %s not allowed", typenames[t]);
959 SimpleStatement(pr_opcodes[OP_INC_F].op, e->ofs, e2->ofs, e->ofs);
960 dontcomplain = true;
961 return e;
962 }
963 if (PR_Check("--"))
964 {
965 e = PR_Expression (1, false);
966 t = PR_GetType(e);
967 if (t == ev_int)
968 {
969 pr_immediate_type = &type_int;
970 pr_immediate._int = 1;
971 }
972 else
973 {
974 pr_immediate_type = &type_float;
975 pr_immediate._float = 1;
976 }
977 e2 = PR_ParseImmediate();
978 HashImmediate();
979 if (t != ev_float && t != ev_int)
980 PR_ParseError("Type mismatch for --, %s not allowed", typenames[t]);
981
982 SimpleStatement(pr_opcodes[OP_DEC_F].op, e->ofs, e2->ofs, e->ofs);
983 dontcomplain = true;
984 return e;
985 }
986
987 if (PR_Check ("!"))
988 {
989 e = PR_Expression (NOT_PRIORITY, false);
990 t = PR_GetType(e);
991 if (t == ev_float || t == ev_int)
992 e2 = PR_Statement (&pr_opcodes[OP_NOT_F], e, 0);
993 else if (t == ev_string)
994 e2 = PR_Statement (&pr_opcodes[OP_NOT_S], e, 0);
995 else if (t == ev_entity)
996 e2 = PR_Statement (&pr_opcodes[OP_NOT_ENT], e, 0);
997 else if (t == ev_vector)
998 e2 = PR_Statement (&pr_opcodes[OP_NOT_V], e, 0);
999 else if (t == ev_function)
1000 e2 = PR_Statement (&pr_opcodes[OP_NOT_FNC], e, 0);
1001 else
1002 {
1003 e2 = NULL; // shut up compiler warning;
1004 PR_ParseError ("type mismatch for ! %s not allowed", typenames[t]);
1005 }
1006 return e2;
1007 }
1008
1009
1010 if (PR_Check("&"))
1011 {
1012 e = PR_Expression(1, false);
1013 t = e->type->type;
1014 if (t == ev_string || t == ev_field || t == ev_entity || t == ev_function)
1015 return PR_Cast(e, &type_float);
1016 //e->cast = ev_float;
1017 else if ((t == ev_float) || (t== ev_int))
1018 return PR_Cast(e, &type_pointer);
1019 //e->cast = ev_pointer;
1020 else
1021 PR_ParseError ("bad type for &. %s not allowed", typenames[t]);
1022 return e;
1023 }
1024
1025 if (PR_Check("*"))
1026 {
1027 e = PR_Expression(1, false);
1028 t = e->type->type;
1029 if ((t == ev_float) || (t== ev_int))
1030 return PR_Cast(e, &type_entity);
1031 //e->cast = ev_entity;
1032 else
1033 PR_ParseError ("bad type for *. %s not allowed", typenames[t]);
1034 return e;
1035 }
1036
1037 if (PR_Check("@"))
1038 {
1039 e = PR_Expression(1, false);
1040 t = e->type->type;
1041 if ((t == ev_float) || (t== ev_int))
1042 return PR_Cast(e, &type_string);
1043 //e->cast = ev_string;
1044 else
1045 PR_ParseError ("bad type for @. %s not allowed", typenames[t]);
1046 return e;
1047 }
1048
1049
1050 if (PR_Check("("))
1051 {
1052 // this ought to slow it down...
1053 if (!STRCMP("float", pr_token) || !STRCMP("vector", pr_token) || !STRCMP("int", pr_token)
1054 || !STRCMP("string", pr_token) || !STRCMP("entity", pr_token) || !STRCMP(".", pr_token) || !STRCMP("void", pr_token))
1055 {
1056 ty = PR_ParseType();
1057 PR_Expect(")");
1058 e = PR_Expression(1, false);
1059 return PR_Cast(e, ty);
1060 }
1061 e = PR_Expression (TOP_PRIORITY, false);
1062 PR_Expect (")");
1063 return e;
1064 }
1065 }
1066 return PR_ParseValue ();
1067 }
1068
1069
1070 /*
1071 ==============
1072 PR_Expression
1073 ==============
1074 */
1075
PR_Expression(int priority,boolean returnused)1076 def_t *PR_Expression (int priority, boolean returnused)
1077 {
1078 opcode_t *op, *oldop;
1079 def_t *e, *e2, *e3, *e4;
1080 etype_t type_a, type_b, type_c;
1081 dstatement_t *patch1, *patch2;
1082 int i;
1083 int index=0;
1084
1085 if (priority == 0)
1086 return PR_Term ();
1087
1088 ecorrection = NULL;
1089 e = PR_Expression (priority-1, returnused);
1090 if (e->type->type == ev_int)
1091 expectint = true;
1092 e4 = e;
1093 while (1)
1094 {
1095
1096 if (priority == 1 && PR_Check ("(") )
1097 {
1098 dontcomplain = true;
1099 e3 = NULL;
1100 if (returnused)
1101 {
1102 e3 = GimmeATempFoo(3);
1103 e3->type = def_ret.type;
1104 PR_Statement(&pr_opcodes[OP_STORE_V], &def_ret, e3);
1105 }
1106 e = PR_ParseFunctionCall (e);
1107
1108 if (e3 != NULL)
1109 ecorrection = e3;
1110 return e;
1111 }
1112 // FrikaC : not good CHEDDAR
1113 if (pr_token[0] == '?' && !pr_token[1])
1114 {
1115 if (priority != 6)
1116 break;
1117 PR_Lex();
1118 PR_Statement(&pr_opcodes[OP_IFNOT], e, 0);
1119 patch1 = &statements[numstatements - 1];
1120 e = PR_Expression(TOP_PRIORITY, false);
1121 if (type_size[e->type->type] == 3)
1122 {
1123 e2 = GimmeATempFoo(3);
1124 PR_Statement (&pr_opcodes[OP_STORE_V], e, e2);
1125 }
1126 else
1127 {
1128 e2 = GimmeATempFoo(1);
1129 PR_Statement (&pr_opcodes[OP_STORE_F], e, e2);
1130 }
1131 PR_Expect(":");
1132 patch2 = &statements[numstatements];
1133 SimpleStatement(OP2_GOTO, 0, 0, 0);
1134 patch1->b = &statements[numstatements] - patch1;
1135 e = PR_Expression(TOP_PRIORITY, false);
1136 if (type_size[e->type->type] == 3)
1137 PR_Statement (&pr_opcodes[OP_STORE_V], e, e2);
1138 else
1139 PR_Statement (&pr_opcodes[OP_STORE_F], e, e2);
1140 patch2->a = &statements[numstatements] - patch2;
1141 return e2;
1142 // ugh!
1143 }
1144
1145
1146 index = (pr_token[0] + pr_token[1]) & (OPTABLESIZE - 1);
1147 op = pr_opcodes + optable[index];
1148 type_c = ev_void;
1149
1150 if (op->priority != priority || STRCMP(op->name, pr_token))
1151 break;
1152 if ((unsigned)(optable[index] - OP_ARRAY_F) < 7)
1153 expectint = true;
1154 PR_Lex();
1155
1156 if (pr_optimize_logicops && conditional)
1157 {
1158 if (op->op == OP2_AND)
1159 {
1160 patch1 = &statements[numstatements];
1161 SimpleStatement(OP2_IFNOT, e->ofs,0,0);
1162
1163 }
1164 else if (op->op == OP2_OR)
1165 {
1166 patch1 = &statements[numstatements];
1167 SimpleStatement(OP2_IF, e->ofs,0,0);
1168 }
1169 }
1170 else if ( optable[index] >= OP_INC_F )
1171 {
1172 if (e->constant)
1173 PR_ParseWarning(1, "Assignment to constant");
1174 if (e->type->type != ev_float && e->type->type != ev_int)
1175 PR_ParseError("Type mismatch for %s", op->name);
1176 if (e->type->type == ev_int)
1177 {
1178 pr_immediate_type = &type_int;
1179 pr_immediate._int = 1;
1180 expectint = true;
1181 }
1182 else
1183 {
1184 pr_immediate_type = &type_float;
1185 pr_immediate._float = 1;
1186 expectint = false;
1187 }
1188 e2 = PR_ParseImmediate();
1189 dontcomplain = true;
1190 SimpleStatement(op->op, e->ofs, e2->ofs, e->ofs);
1191 return e;
1192 }
1193
1194 if ( op->right_associative )
1195 {
1196 // if last statement is an indirect, change it to an address of
1197 if (!shortened_store && ((unsigned)(statements[numstatements-1].op - OP2_LOAD_F) < 6))
1198 {
1199 statements[numstatements-1].op = OP2_ADDRESS;
1200 if (e->type->arraysize)
1201 {
1202 def_pointer.type->aux_type = e->type->aux_type;
1203 e->type = def_pointer.type;
1204 }
1205 else
1206 {
1207 def_pointer.type->aux_type = e->type;
1208 e->type = def_pointer.type;
1209 }
1210 }
1211 e2 = PR_Expression (priority, e->ofs == OFS_RETURN);
1212 if (ecorrection)
1213 {
1214 e = ecorrection;
1215 ecorrection = NULL;
1216 }
1217 }
1218 else
1219 {
1220 if ((unsigned)(optable[index] - OP_ARRAY_F) < 7)
1221 {
1222 e2 = PR_Expression (TOP_PRIORITY, e->ofs == OFS_RETURN);
1223 if (e2->type->type != ev_int)
1224 PR_ParseWarning(1, "Array index should be type int");
1225 if (ecorrection)
1226 {
1227 e = ecorrection;
1228 ecorrection = NULL;
1229 }
1230 PR_Expect("]");
1231 if (e->type->arraysize)
1232 type_c = e->type->aux_type->type;
1233 }
1234 else
1235 {
1236 e2 = PR_Expression (priority-1, e->ofs == OFS_RETURN);
1237 if (ecorrection)
1238 {
1239 e = ecorrection;
1240 ecorrection = NULL;
1241 }
1242 }
1243 }
1244 newop:
1245 // type check
1246 type_a = PR_GetType(e);
1247 type_b = PR_GetType(e2);
1248
1249
1250 // to keep the op count low, we'll lie
1251
1252 if ((type_a == ev_int && type_b == ev_float) || (type_a == ev_float && type_b == ev_int))
1253 PR_ParseWarning(1, "Mixed float and int types");
1254 if (op->type_a->type->type == ev_float && type_a == ev_float && expectint)
1255 PR_ParseWarning(1, "Expecting int, float a parameter found");
1256 if (op->type_b->type->type == ev_float && type_b == ev_float && expectint)
1257 PR_ParseWarning(1, "Expecting int, floar parameter b found");
1258
1259 if (op->name[0] == '.')// field access gets type from field
1260 {
1261 if (e2->type->aux_type)
1262 type_c = e2->type->aux_type->type;
1263 else
1264 type_c = ev_bad; // not a field
1265 }
1266
1267 if (type_a == ev_int)
1268 {
1269 type_a = ev_float;
1270 expectint = true;
1271 }
1272 if (type_b == ev_int)
1273 {
1274 type_b = ev_float;
1275 expectint = true;
1276 }
1277 if (type_c == ev_int)
1278 type_c = ev_float; // blarg
1279
1280 oldop = op;
1281 while (type_a != op->type_a->type->type || type_b != op->type_b->type->type || (type_c != ev_void && type_c != op->type_c->type->type) )
1282 {
1283 op++;
1284 if (!op->name || STRCMP(op->name, oldop->name))
1285 PR_ParseError ("type mismatch for %s. Types %s and %s not allowed", oldop->name, typenames[type_a], typenames[type_b]);
1286 }
1287
1288 if (type_a == ev_pointer && statements[numstatements-1].op == OP2_ADDRESS && type_b != e->type->aux_type->type)
1289 PR_ParseError ("type mismatch for %s", op->name);
1290
1291 if (optable[index] >= OP_ADD_STORE_F)
1292 {
1293 dontcomplain = true;
1294
1295 if (e->constant)
1296 PR_ParseWarning(1, "Assignment to constant");
1297
1298 // SimpleStatement(op->op, e->ofs, e2->ofs, e->ofs);
1299 e = PR_Statement(&pr_opcodes[op->op], e, e2); // hack hack hack
1300 e2 = e4;
1301 op = &pr_opcodes[OP_STORE_F];
1302 index = 0;
1303 goto newop;
1304 }
1305
1306 if (pr_optimize_logicops && conditional)
1307 {
1308 if (op->op == OP2_AND || op->op == OP2_OR)
1309 {
1310 patch1->b = &statements[numstatements] - patch1;
1311 num_logic_jumps++;
1312 }
1313 }
1314
1315 if (op->right_associative)
1316 {
1317 if ((unsigned)(op->op - OP2_STORE_F) < 6)
1318 {
1319 if (e->constant)
1320 PR_ParseWarning(1, "Assignment to constant");
1321 }
1322 dontcomplain = true;
1323 if (conditional)
1324 PR_ParseWarning(2, "Assignment in conditional");
1325 e = PR_Statement (op, e2, e);
1326 }
1327 else
1328 e = PR_Statement (op, e, e2);
1329 if (e4->type->arraysize)
1330 e->type = e4->type->aux_type;
1331 else if (type_c != ev_void) // field access gets type from field
1332 e->type = e2->type->aux_type;
1333
1334 else if (op->type_c->type->type == ev_float && expectint)
1335 e->type = &type_int;
1336 if (e->type && e->type->type == ev_int)
1337 expectint = true;
1338 else
1339 expectint = false;
1340
1341 }
1342 expectint = false;
1343
1344 return e;
1345
1346 }
1347 /* ---------------
1348
1349 FrikaC ---- Label Stuff
1350
1351 ------------------- */
1352
1353 int num_continues;
1354 int num_breaks;
1355 int pr_continues[32];
1356 int pr_breaks[32];
1357
1358 extern int PR_FindDefine (char *name);
1359
GetLabelDef(char * tname,boolean makenew)1360 int GetLabelDef (char *tname, boolean makenew)
1361 {
1362 dstatement_t *curpos;
1363 int i;
1364
1365 curpos = &statements[numstatements];
1366 i = PR_FindDefine(tname);
1367
1368 if (i)
1369 {
1370 if(makenew)
1371 {
1372 if(pr_defines[i].defined)
1373 PR_ParseWarning(1, "redifinition of label %s", tname);
1374 pr_defines[i].defined = true;
1375 statements[pr_defines[i].value._int].a = curpos
1376 - &statements[pr_defines[i].value._int] ;
1377 pr_defines[i].value._int = numstatements;
1378 return &statements[pr_defines[i].value._int] - curpos;
1379 }
1380 else
1381 {
1382 if(pr_defines[i].defined)
1383 return &statements[pr_defines[i].value._int] - curpos;
1384 }
1385 }
1386 num_defines++;
1387 pr_defines[num_defines].name = (char *)PR_Malloc(strlen(tname) + 1);
1388 strcpy(pr_defines[num_defines].name, tname);
1389 macrohash[hash(tname)] = num_defines;
1390 pr_defines[num_defines].value._int = numstatements;
1391 pr_defines[num_defines].label = true;
1392 if (makenew)
1393 pr_defines[num_defines].defined = true;
1394 else
1395 pr_defines[num_defines].defined = false;
1396
1397 return &statements[pr_defines[num_defines].value._int] - curpos;
1398
1399 }
1400
1401
1402 /*
1403 ============
1404 PR_ParseStatement
1405
1406 ============
1407 */
1408
PR_ParseStatement(void)1409 void PR_ParseStatement (void)
1410 {
1411 def_t *e;
1412 dstatement_t *patch1, *patch2, *patch3;
1413 int old_numstatements, numtemp;
1414 dstatement_t temp[32];
1415 int linenum[32];
1416 int breaks, continues;
1417 int i;
1418
1419 // FrikaC: clean up temps
1420 memset(used_temps, 0, sizeof(used_temps));
1421
1422 if (PR_Check ("{"))
1423 {
1424 while (!PR_Check ("}"))
1425 PR_ParseStatement ();
1426 return;
1427 }
1428
1429 if (PR_Check("return"))
1430 {
1431 if (PR_Check (";"))
1432 {
1433 if(pr_scope->type->aux_type != &type_void)
1434 PR_ParseWarning(2, "%s must return a value", pr_scope->name);
1435 PR_Statement (&pr_opcodes[OP_RETURN], 0, 0);
1436 return;
1437 }
1438 e = PR_Expression (TOP_PRIORITY, false);
1439 PR_Expect (";");
1440 if(pr_scope->type->aux_type != e->type)
1441 {
1442 if (pr_scope->type->aux_type == &type_void)
1443 PR_ParseWarning(2, "%s does not return a value", pr_scope->name);
1444 else
1445 {
1446 PR_ParseWarning(2, "%s: Type mismatch on return. Expected %s found %s", pr_scope->name,
1447 typenames[pr_scope->type->aux_type->type], typenames[e->type->type]);
1448 }
1449 }
1450 PR_Statement (&pr_opcodes[OP_RETURN], e, 0);
1451 return;
1452 }
1453
1454 if (PR_Check("while"))
1455 {
1456 PR_Expect ("(");
1457 patch2 = &statements[numstatements];
1458 continues = num_continues;
1459 breaks = num_breaks;
1460 conditional = true;
1461 e = PR_Expression (TOP_PRIORITY, false);
1462 conditional = false;
1463 PR_Expect (")");
1464 PR_Statement (&pr_opcodes[OP_IFNOT], e, 0);
1465 patch1 = &statements[numstatements-1];
1466 PR_ParseStatement ();
1467 SimpleStatement(OP2_GOTO, patch2 - &statements[numstatements], 0, 0);
1468 patch1->b = &statements[numstatements] - patch1;
1469 if (breaks != num_breaks)
1470 {
1471 for(i = breaks; i < num_breaks; i++)
1472 {
1473 patch1 = &statements[pr_breaks[i]];
1474 statements[pr_breaks[i]].a = &statements[numstatements] - patch1;
1475 }
1476 num_breaks = breaks;
1477 }
1478 if (continues != num_continues)
1479 {
1480 for(i = continues; i < num_continues; i++)
1481 {
1482 statements[pr_continues[i]].a = patch2 - &statements[pr_continues[i]];
1483 }
1484 num_continues = continues;
1485 }
1486 return;
1487 }
1488 if (PR_Check("for"))
1489 {
1490 PR_Expect("(");
1491 if (!PR_Check(";"))
1492 {
1493 PR_Expression(TOP_PRIORITY, false);
1494 PR_Expect(";");
1495 }
1496
1497 patch2 = &statements[numstatements];
1498 conditional = true;
1499 e = PR_Expression(TOP_PRIORITY, false);
1500 conditional = false;
1501 PR_Expect(";");
1502 // I dunno -- do you know?
1503 continues = num_continues;
1504 breaks = num_breaks;
1505
1506 old_numstatements = numstatements;
1507 PR_Expression(TOP_PRIORITY, false);
1508 numtemp = numstatements - old_numstatements;
1509 if (numtemp > 32)
1510 PR_ParseError("Update expression too large");
1511 numstatements = old_numstatements;
1512 for (i = 0 ; i < numtemp ; i++)
1513 {
1514 linenum[i] = statement_linenums[numstatements + i];
1515 temp[i] = statements[numstatements + i];
1516 }
1517
1518 PR_Expect(")");
1519 PR_Statement(&pr_opcodes[OP_IFNOT], e, 0);
1520 patch1 = &statements[numstatements-1];
1521 PR_ParseStatement();
1522 patch3 = &statements[numstatements];
1523 for (i = 0 ; i < numtemp ; i++)
1524 {
1525 statement_linenums[numstatements] = linenum[i];
1526 statements[numstatements++] = temp[i];
1527 }
1528 SimpleStatement(OP2_GOTO, patch2 - &statements[numstatements], 0, 0);
1529 patch1->b = &statements[numstatements] - patch1;
1530 if (breaks != num_breaks)
1531 {
1532 for(i = breaks; i < num_breaks; i++)
1533 {
1534 patch1 = &statements[pr_breaks[i]];
1535 statements[pr_breaks[i]].a = &statements[numstatements] - patch1;
1536 }
1537 num_breaks = breaks;
1538 }
1539 if (continues != num_continues)
1540 {
1541 for(i = continues; i < num_continues; i++)
1542 {
1543 patch1 = &statements[pr_continues[i]];
1544 statements[pr_continues[i]].a = patch3 - patch1;
1545 }
1546 num_continues = continues;
1547 }
1548 return;
1549 }
1550 if (PR_Check("do"))
1551 {
1552 patch1 = &statements[numstatements];
1553 continues = num_continues;
1554 breaks = num_breaks;
1555 PR_ParseStatement ();
1556 PR_Expect ("while");
1557 PR_Expect ("(");
1558 conditional = true;
1559 e = PR_Expression (TOP_PRIORITY, false);
1560 conditional = false;
1561 PR_Expect (")");
1562 PR_Expect (";");
1563 PR_Statement (&pr_opcodes[OP_IF], e, 0);
1564 patch2 = &statements[numstatements - 1];
1565 patch2->b = patch1 - patch2;
1566
1567 // God I mucked a lot of stuff up...
1568 if (breaks != num_breaks)
1569 {
1570 for(i = breaks; i < num_breaks; i++)
1571 {
1572 patch2 = &statements[pr_breaks[i]];
1573 statements[pr_breaks[i]].a = &statements[numstatements] - patch2;
1574 }
1575 num_breaks = breaks;
1576 }
1577 if (continues != num_continues)
1578 {
1579 for(i = continues; i < num_continues; i++)
1580 {
1581 patch2 = &statements[pr_continues[i]];
1582 statements[pr_continues[i]].a = patch1 - patch2;
1583 }
1584 num_continues = continues;
1585 }
1586 return;
1587 }
1588
1589 if (PR_Check("local"))
1590 {
1591
1592 PR_ParseDefs ();
1593 locals_end = numpr_globals;
1594 return;
1595 }
1596
1597 if (PR_Check("goto"))
1598 {
1599 //PR_Lex();
1600 if (pr_token_type != tt_name)
1601 {
1602 PR_ParseError("invalid label name \"%s\"", pr_token);
1603 return;
1604 }
1605 SimpleStatement(OP2_GOTO, GetLabelDef(pr_token, false), 0, 0);
1606 PR_Lex();
1607 PR_Expect(";");
1608 return;
1609 }
1610 if (PR_Check("state"))
1611 {
1612 PR_Expect("[");
1613 PR_ParseState();
1614 PR_Expect(";");
1615 return;
1616 }
1617 if (PR_Check(":")) //labels
1618 {
1619 if (pr_token_type != tt_name)
1620 {
1621 PR_ParseError("invalid label name \"%s\"", pr_token);
1622 return;
1623 }
1624 GetLabelDef(pr_token, true);
1625 PR_Lex();
1626 return;
1627 }
1628
1629 if (PR_Check("if"))
1630 {
1631 PR_Expect ("(");
1632 conditional = true;
1633 e = PR_Expression (TOP_PRIORITY, false);
1634 conditional = false;
1635 PR_Expect (")");
1636
1637 PR_Statement (&pr_opcodes[OP_IFNOT], e, 0);
1638 patch1 = &statements[numstatements-1];
1639
1640 PR_ParseStatement ();
1641
1642 if (PR_Check ("else"))
1643 {
1644 patch2 = &statements[numstatements];
1645 if((&statements[numstatements] - patch1) == 1)
1646 PR_ParseWarning(1, "Null 'if' statement");
1647 PR_Statement (&pr_opcodes[OP_GOTO], 0, 0);
1648 patch1->b = &statements[numstatements] - patch1;
1649 PR_ParseStatement ();
1650 patch2->a = &statements[numstatements] - patch2;
1651 if((&statements[numstatements] - patch2) == 1)
1652 PR_ParseWarning(1, "Null 'else' statement");
1653
1654 }
1655 else
1656 {
1657 if((&statements[numstatements] - patch1) == 1)
1658 PR_ParseWarning(1, "Null 'if' statement");
1659
1660 patch1->b = &statements[numstatements] - patch1;
1661 }
1662 return;
1663 }
1664 if (PR_Check("break"))
1665 {
1666 if (num_breaks > 32)
1667 PR_ParseError("Cannot have more than 32 breaks in a loop");
1668 pr_breaks[num_breaks] = numstatements;
1669 PR_Statement (&pr_opcodes[OP_GOTO], 0, 0);
1670 num_breaks++;
1671 PR_Expect(";");
1672 return;
1673 }
1674 if (PR_Check("continue"))
1675 {
1676 if (num_continues > 32)
1677 PR_ParseError("Cannot have more than 32 continues in a loop");
1678 pr_continues[num_continues] = numstatements;
1679 PR_Statement (&pr_opcodes[OP_GOTO], 0, 0);
1680 num_continues++;
1681 PR_Expect(";");
1682 return;
1683 }
1684 //FrikaC begin
1685
1686
1687 if (!STRCMP("float", pr_token) || !STRCMP("vector", pr_token) || !STRCMP("int", pr_token)
1688 || !STRCMP("string", pr_token) || !STRCMP("entity", pr_token) || !STRCMP("const", pr_token) || !STRCMP("var", pr_token))
1689 {
1690
1691 PR_ParseDefs ();
1692 locals_end = numpr_globals;
1693 return;
1694 }
1695
1696 // FrikaC end
1697 dontcomplain = false;
1698 e = PR_Expression (TOP_PRIORITY, false);
1699 if ((e->type->type != ev_void) && !dontcomplain)
1700 PR_ParseWarning(2, "No operation performed");
1701 PR_Expect (";");
1702 }
1703
1704
1705 /*
1706 ==============
1707 PR_ParseState
1708
1709 States are special functions made for convenience. They automatically
1710 set frame, nextthink (implicitly), and think (allowing forward definitions).
1711
1712 // void() name = [framenum, nextthink] {code}
1713 // expands to:
1714 // function void name ()
1715 // {
1716 // self.frame=framenum;
1717 // self.nextthink = time + 0.1;
1718 // self.think = nextthink
1719 // <code>
1720 // };
1721 ==============
1722 */
PR_ParseState(void)1723 void PR_ParseState (void)
1724 {
1725 char *name;
1726 def_t *s1, *def;
1727
1728 if (pr_token_type != tt_immediate || pr_immediate_type != &type_float)
1729 PR_ParseError ("state frame must be a number");
1730 s1 = PR_ParseImmediate ();
1731 PR_Lex();
1732 PR_Expect (",");
1733
1734 name = PR_ParseName ();
1735 def = PR_GetDef (&type_function, name,0, true, 1, 0);
1736
1737 PR_Expect ("]");
1738
1739 PR_Statement (&pr_opcodes[OP_STATE], s1, def);
1740 }
1741
1742 /*
1743 ============
1744 PR_ParseImmediateStatements
1745
1746 Parse a function body
1747 ============
1748 */
PR_ParseImmediateStatements(type_t * type)1749 function_t *PR_ParseImmediateStatements (type_t *type)
1750 {
1751 int i;
1752 function_t *f;
1753 def_t *defs[MAX_PARMS + MAX_EXTRA_PARMS];
1754 def_t *e2;
1755 f = (struct function_s *) PR_Malloc (sizeof(function_t));
1756
1757 //
1758 // check for builtin function definition #1, #2, etc
1759 //
1760 if (PR_Check ("#"))
1761 {
1762 if (pr_token_type != tt_immediate || pr_immediate_type != &type_float || pr_immediate._float != (int)pr_immediate._float)
1763 PR_ParseError("Bad builtin immediate");
1764 f->builtin = (int) pr_immediate._float;
1765 PR_Lex();
1766 return f;
1767 }
1768
1769 f->builtin = 0;
1770 //
1771 // define the parms
1772 //
1773 for (i=0 ; i<type->num_parms ; i++)
1774 {
1775 defs[i] = PR_GetDef (type->parm_types[i], pr_parm_names[i], pr_scope, true, -1, -1);
1776 if (i > MAX_PARMS)
1777 continue;
1778 f->parm_ofs[i] = defs[i]->ofs;
1779 if (i > 0 && f->parm_ofs[i] < f->parm_ofs[i-1])
1780 Sys_Error("bad parm order");
1781 }
1782
1783 f->code = numstatements;
1784 if (type->num_parms > MAX_PARMS) // locutus
1785 {
1786 for (i = MAX_PARMS; i < type->num_parms; i++)
1787 {
1788 if (!extra_parms[i - MAX_PARMS])
1789 {
1790 e2 = (struct def_s *) PR_Malloc (sizeof(def_t));
1791 e2->ofs = numpr_globals;
1792 e2->name = "extra parm";
1793 pr_global_defs[numpr_globals] = e2;
1794 numpr_globals += 3;
1795 extra_parms[i - MAX_PARMS] = e2;
1796 }
1797 if (defs[i]->type->type != ev_vector)
1798 PR_Statement (&pr_opcodes[OP_STORE_F], extra_parms[i - MAX_PARMS], defs[i]);
1799 else
1800 PR_Statement (&pr_opcodes[OP_STORE_V], extra_parms[i - MAX_PARMS], defs[i]);
1801 }
1802 }
1803 //
1804 // check for a state opcode
1805 //
1806 if (PR_Check ("["))
1807 PR_ParseState ();
1808
1809 //
1810 // parse regular statements
1811 //
1812 PR_Expect ("{");
1813
1814 while (!PR_Check("}"))
1815 PR_ParseStatement ();
1816 // this is cheap
1817 if (type->aux_type != &type_void)
1818 if (statements[numstatements - 1].op != OP2_RETURN)
1819 PR_ParseWarning(2, "%s: not all control paths return a value", pr_scope->name );
1820 // emit an end of statements opcode
1821 PR_Statement (pr_opcodes, 0,0);
1822
1823
1824 return f;
1825 }
1826
1827
PR_DefineElements(def_t * def,int save)1828 int PR_DefineElements(def_t *def, int save)
1829 {
1830 def_t *elem;
1831 int i, flag = true, start;
1832 char element[MAX_NAME];
1833 if (!def->constant)
1834 def->defined = true;
1835
1836 start = numpr_globals;
1837 for (i = 0; i < def->type->arraysize; i++)
1838 {
1839 sprintf(element, "%s_%i", def->name, i);
1840
1841 if (def->type->aux_type->arraysize)
1842 {
1843 elem = PR_GetDef(def->type->aux_type, element, def->scope, false, -1, save);
1844 if (elem)
1845 {
1846 flag = PR_DefineElements(elem, save);
1847 start = def->arraystart;
1848 }
1849 else
1850 {
1851 elem = PR_GetDef(&type_void, element, def->scope, true, -1, save);
1852 elem->type = def->type->aux_type;
1853 elem->constant = true;
1854 elem->defined = true;
1855 elem->save = false;
1856 flag = false;
1857 }
1858 }
1859 else
1860 elem = PR_GetDef(def->type->aux_type, element, def->scope, true, -1, save);
1861 elem->defined = true;
1862 }
1863 def->arraystart = start;
1864 return flag;
1865 }
PR_GetArray(def_t * def,int save)1866 void PR_GetArray (def_t *def, int save)
1867 {
1868 while(!PR_DefineElements(def, save));
1869 };
1870
1871 /*
1872 ============
1873 PR_GetDef
1874
1875 If type is NULL, it will match any type
1876 If allocate is true, a new def will be allocated if it can't be found
1877 ============
1878 */
1879
PR_GetDef(type_t * type,char * name,def_t * scope,boolean allocate,int constant,int save)1880 def_t *PR_GetDef (type_t *type, char *name, def_t *scope, boolean allocate, int constant, int save)
1881 {
1882 def_t *def, *elem;
1883 char element[MAX_NAME];
1884
1885 int index, i, m;
1886 struct hash_element *cell;
1887
1888 index = hash(name);
1889 for (cell = htable[index]; cell != NULL; cell = cell->next)
1890 {
1891 def = cell->def;
1892 if ( !STRCMP(def->name, name) )
1893 {
1894 if (def->scope && (def->scope != scope))
1895 {
1896 if (!scope && allocate)
1897 PR_ParseWarning(3, "%s defined as local in %s", def->name, def->scope->name);
1898 continue;
1899 }
1900 if (type && def->type->type != type->type)
1901 {
1902
1903 if (scope == def->scope)
1904 PR_ParseError ("Type mismatch on redeclaration of %s (see original definition %s(%i))", name, def->s_file, def->line);
1905 else
1906 {
1907 PR_ParseWarning(2, "%s redeclared on different scope (see original definition %s(%i))", name, def->s_file, def->line);
1908 continue;
1909 }
1910 }
1911 else if (type && (def->type->type == ev_field))
1912 {
1913 if (type->aux_type->type != def->type->aux_type->type)
1914 {
1915 if (scope == def->scope)
1916 PR_ParseWarning (1, "Type mismatch on redeclaration of %s (see original definition %s(%i))", name, def->s_file, def->line);
1917 else
1918 {
1919 PR_ParseWarning(2, "%s redeclared on different scope (see original definition %s(%i))", name, def->s_file, def->line);
1920 continue;
1921 }
1922 }
1923 }
1924 else if (type && (def->type->type == ev_function))
1925 {
1926 if (type->aux_type->type != def->type->aux_type->type)
1927 PR_ParseWarning (1, "Type mismatch on redeclaration of %s (see original definition %s(%i))", name, def->s_file, def->line);
1928 else if (type->num_parms != def->type->num_parms)
1929 PR_ParseWarning (1, "%s redeclared with different number of parms (see original definition %s(%i))", name, def->s_file, def->line);
1930 else
1931 {
1932 for (i = 0; i < type->num_parms; i++)
1933 if (type->parm_types[i]->type != def->type->parm_types[i]->type)
1934 PR_ParseWarning (1, "%s rededeclared with different parms (see original definition %s(%i))", name, def->s_file, def->line);
1935 }
1936 }
1937 if (scope && allocate)
1938 PR_ParseWarning(1, "%s redeclared", name);
1939
1940 pr_global_refs[def->ofs]++;
1941 return def;
1942 }
1943 }
1944
1945 if (!allocate)
1946 return NULL;
1947
1948
1949 // allocate a new def
1950 def = (struct def_s *) PR_Malloc (sizeof(def_t));
1951 def->next = NULL;
1952 pr.def_tail->next = def;
1953 pr.def_tail = def;
1954
1955 cell = (struct hash_element *) PR_Malloc (sizeof(struct hash_element));
1956 cell->next = htable[index];
1957 cell->def = def;
1958 htable[index] = cell;
1959 stats[index]++;
1960
1961 def->name = (char *) PR_Malloc(strlen(name)+1);
1962 strcpy(def->name, name);
1963 def->type = type;
1964
1965
1966 if (constant == 1)
1967 def->constant = 1;
1968 else if (constant == -1)
1969 def->constant = 0;
1970 else if (type->arraysize)
1971 def->constant = 0;
1972 else if (scope)
1973 def->constant = 0;
1974 else if ((type->type == ev_field) || (type->type == ev_function))
1975 def->constant = 1;
1976 else
1977 def->constant = 0;
1978
1979 if (save == 1)
1980 def->save = 1;
1981 else if (save == -1)
1982 def->save = 0;
1983 else if (scope)
1984 def->save = 0;
1985 else if ((type->type == ev_field) && (def->constant == 1))
1986 def->save = 1;
1987 else if (def->constant)
1988 def->save = 0;
1989 else
1990 def->save = 1;
1991
1992 def->s_file = s_file + strings;
1993 def->line = pr_source_line;
1994 def->scope = scope;
1995 def->tempnext = NULL;
1996
1997 def->ofs = numpr_globals;
1998 pr_global_defs[numpr_globals] = def;
1999
2000 if (!pr_system) // pr_sytem == true means system defs are done
2001 pr_global_refs[numpr_globals] = 1;
2002 if(!STRCMP(def->name, "end_sys_fields"))
2003 pr_system = true;
2004 //
2005 // make automatic defs for the vectors elements
2006 // .origin can be accessed as .origin_x, .origin_y, and .origin_z
2007 //
2008 if (type->type == ev_vector)
2009 {
2010 sprintf (element, "%s_x",name);
2011 elem = PR_GetDef (&type_float, element, scope, true, constant, save);
2012 elem->defined = true; // hack
2013 pr_global_refs[numpr_globals]++;// FrikaC
2014
2015 sprintf (element, "%s_y",name);
2016 elem = PR_GetDef (&type_float, element, scope, true, constant, save);
2017 elem->defined = true;
2018 pr_global_refs[numpr_globals]++;// FrikaC
2019
2020 sprintf (element, "%s_z",name);
2021 elem = PR_GetDef (&type_float, element, scope, true, constant, save);
2022 elem->defined = true;
2023 pr_global_refs[numpr_globals]++;// FrikaC
2024
2025 }
2026 else
2027 numpr_globals += type_size[type->type];
2028
2029 if ((type->type == ev_field) && def->constant)
2030 {
2031 *(int *)&pr_globals[def->ofs] = pr.size_fields;
2032 def->defined = true;
2033
2034 if (type->aux_type->type == ev_vector)
2035 {
2036 sprintf (element, "%s_x",name);
2037 PR_GetDef (&type_floatfield, element, scope, true, constant, save);
2038
2039 sprintf (element, "%s_y",name);
2040 PR_GetDef (&type_floatfield, element, scope, true, constant, save);
2041
2042 sprintf (element, "%s_z",name);
2043 PR_GetDef (&type_floatfield, element, scope, true, constant, save);
2044 }
2045 else
2046 pr.size_fields += type_size[type->aux_type->type];
2047 }
2048 else if (type->arraysize)
2049 PR_GetArray(def, save);
2050 // if (pr_dumpasm)
2051 // PR_PrintOfs (def->ofs);
2052
2053 return def;
2054 }
2055
2056 /*
2057 ================
2058 PR_ParseDefs
2059
2060 Called at the outer layer and when a local statement is hit
2061 ================
2062 */
2063 int constmode = 0;
2064
PR_ParseDefs(void)2065 void PR_ParseDefs (void)
2066 {
2067 char *name;
2068 type_t *type, *check;
2069 def_t *def, *odef;
2070 function_t *f;
2071 dfunction_t *df;
2072 int i, size;
2073 int locals_start, test;
2074 int constant = 0;
2075 int save = 0;
2076 static char ident[MAX_NAME];
2077
2078 struct hash_element *cell = NULL;
2079 if (PR_Check("nosave"))
2080 save = -1;
2081 if (PR_Check("var"))
2082 constant = -1;
2083 else if (PR_Check("const"))
2084 {
2085 constmode = 1;
2086 constant = 1;
2087 }
2088 else if (constmode)
2089 constant = -1;
2090
2091 type = PR_ParseType ();
2092
2093 do
2094 {
2095 strcpy(ident, PR_ParseName());
2096
2097 if (PR_Check("(") && type->type != ev_function)
2098 {
2099 // HexenC/C/C++ style function declaration
2100 type = PR_ParseTypeFunction(type);
2101 }
2102 if (!STRCMP(pr_token, "="))
2103 {
2104 if (constant == 0)
2105 constant = 1;
2106 if (type->type == ev_int)
2107 expectint = true;
2108 }
2109 def = PR_GetDef (type, ident, pr_scope, true, constant, save);
2110 // check for an initialization
2111 if ( PR_Check ("=") || ((type->type == ev_function) && (pr_token[0] == '{')))
2112 {
2113
2114 if (def->defined)
2115 PR_ParseError ("%s redeclared (see previous declaration %s(%i))", ident, def->s_file, def->line);
2116
2117 def->s_file = s_file + strings;
2118 def->line = pr_source_line;
2119 def->defined = true;
2120
2121 if (type->type == ev_function)
2122 {
2123 locals_start = locals_end = numpr_globals;
2124 pr_scope = def;
2125 test = numstatements;
2126 f = PR_ParseImmediateStatements (type);
2127 pr_scope = NULL;
2128 G_FUNCTION(def->ofs) = numfunctions;
2129 f->def = def;
2130 // if (pr_dumpasm)
2131 // PR_PrintFunction (def);
2132
2133 // fill in the dfunction
2134 df = &functions[numfunctions];
2135 numfunctions++;
2136 if (f->builtin)
2137 {
2138 if (pr_optimize_function_names)
2139 df->s_name = f->def->name - strings;
2140 else
2141 df->s_name = CopyString (f->def->name, 0);
2142 num_funcs_saved += strlen(f->def->name) + 1;
2143 df->first_statement = -f->builtin;
2144 }
2145 else
2146 {
2147 df->s_name = CopyString (f->def->name, 0);
2148 df->first_statement = f->code;
2149 }
2150
2151 df->s_file = s_file;
2152 df->numparms = f->def->type->num_parms;
2153 for (i = 0 ; i < df->numparms ; i++)
2154 df->parm_size[i] = type_size[f->def->type->parm_types[i]->type];
2155
2156 if (warninglevel >= 3)
2157 for(i = locals_end; i >= locals_start; i--)
2158 {
2159 if (pr_global_defs[i])
2160 {
2161 if (pr_global_defs[i]->scope == def)
2162 {
2163 if (pr_global_refs[i] == 0)
2164 {
2165 PR_ParseWarning(3, "Unreferenced local variable %s", pr_global_defs[i]->name);
2166 }
2167 else if (pr_global_defs[i]->type->type == ev_vector)
2168 {
2169 // vector types are weird..
2170 if (pr_global_refs[i] + pr_global_refs[i+1] + pr_global_refs[i+2] == 3)
2171 PR_ParseWarning(3, "Unreferenced local variable %s", pr_global_defs[i]->name);
2172 }
2173 }
2174 }
2175 }
2176 df->locals = locals_end - locals_start;
2177 df->parm_start = locals_start;
2178 if (num_breaks != 0)
2179 {
2180 num_breaks = 0;//shup up compiler
2181 PR_ParseError("Illegal break in function %s", strings + df->s_name);
2182 }
2183 if (num_continues != 0)
2184 {
2185 num_continues = 0;
2186 PR_ParseError("Illegal continue in function %s", strings + df->s_name);
2187 }
2188
2189
2190 continue;
2191 }
2192 else if (type->arraysize)
2193 {
2194 i = 1;
2195 check = type->aux_type;
2196 while(check->arraysize)
2197 {
2198 i *= check->arraysize;
2199 check = check->aux_type;
2200 }
2201 size = i * def->type->arraysize + def->arraystart;
2202 if (i == 1)
2203 i = def->arraystart;
2204 else
2205 i += def->arraystart;
2206 if (pr_immediate_type != check)
2207 PR_ParseError ("Wrong immediate type for %s, Expected %s found %s", ident, typenames[check->type], typenames[pr_immediate_type->type]);
2208 }
2209 else if (pr_immediate_type != type)
2210 PR_ParseError ("Wrong immediate type for %s, Expected %s found %s", ident, typenames[type->type], typenames[pr_immediate_type->type]);
2211 if (type->arraysize)
2212 {
2213
2214 do
2215 {
2216 if (pr_token_type != tt_name)
2217 if (pr_immediate_type == &type_string)
2218 pr_immediate.string = CopyString (pr_immediate_string, pr_immediate_strlen);
2219 memcpy (&(pr_globals[i]), &pr_immediate, 4*type_size[pr_immediate_type->type]);
2220 PR_Lex();
2221 i+=type_size[pr_immediate_type->type];
2222 if (i > size)
2223 PR_ParseWarning(1, "%s: too many initializers", def->name);
2224 }
2225 while (PR_Check(","));
2226
2227 }
2228 else if (pr_optimize_defs && (odef = PR_GetImmediate()))
2229 {
2230 PR_GetImmediate();
2231 if (def->ofs == numpr_globals - 1)
2232 {
2233 numpr_globals--;
2234 def->ofs = odef->ofs;
2235 num_defs += 1;
2236
2237 }
2238 else
2239 {
2240 memcpy (pr_globals + def->ofs, pr_globals + odef->ofs, 4*type_size[pr_immediate_type->type]);
2241 }
2242 }
2243 else
2244 {
2245 cell = (struct hash_element *) PR_Malloc (sizeof(struct hash_element));
2246 cell->next = htable[pr_immediate_index];
2247 cell->def = def;
2248 htable[pr_immediate_index] = cell;
2249 stats[pr_immediate_index]++;
2250 if (pr_token_type != tt_name)
2251 if (pr_immediate_type == &type_string)
2252 pr_immediate.string = CopyString (pr_immediate_string, pr_immediate_strlen);
2253
2254 memcpy (pr_globals + def->ofs, &pr_immediate, 4*type_size[pr_immediate_type->type]);
2255 }
2256 PR_Lex ();
2257 }
2258 def->s_file = s_file + strings;
2259 def->line = pr_source_line;
2260 expectint = false;
2261
2262 } while (PR_Check (","));
2263
2264 // PR_Expect (";");
2265 PR_Check(";");
2266
2267
2268 }
2269
2270 /*
2271 ============
2272 PR_CompileFile
2273
2274 compiles the 0 terminated text, adding defintions to the pr structure
2275 ============
2276 */
2277
2278
PR_CompileFile(char * string,char * filename)2279 boolean PR_CompileFile (char *string, char *filename)
2280 {
2281 char *k;
2282 if (!pr.memory)
2283 Sys_Error("PR_CompileFile: Didn't clear");
2284
2285 PR_ClearGrabMacros (); // clear the frame macros
2286 pr_file_p = string;
2287 if (pr_optimize_filenames)
2288 {
2289 k = (char *)PR_Malloc(strlen(filename) + 1);
2290 strcpy(k, filename);
2291 s_file = k - strings;
2292 num_files_saved += strlen(filename) + 1;
2293 }
2294 else
2295 s_file = CopyString (filename, 0);
2296
2297 pr_source_line = 0;
2298
2299 PR_NewLine ();
2300
2301 PR_Lex (); // read first token
2302
2303 while (pr_token_type != tt_eof)
2304 {
2305 if (setjmp(pr_parse_abort))
2306 {
2307 if (++pr_error_count > MAX_ERRORS)
2308 return false;
2309 PR_SkipToSemicolon ();
2310 if (pr_token_type == tt_eof)
2311 return false;
2312 }
2313
2314 pr_scope = NULL; // outside all functions
2315
2316 PR_ParseDefs ();
2317 }
2318
2319 return (pr_error_count == 0) ? true: false;
2320 }