print out profile report above runaway loop counter error
[divverent/darkplaces.git] / prvm_execprogram.h
1
2 // This code isn't #ifdef/#define protectable, don't try.
3
4                 while (1)
5                 {
6                         st++;
7
8 #if PRVMTRACE
9                         PRVM_PrintStatement(st);
10 #endif
11 #if PRVMSTATEMENTPROFILING
12                         prog->statement_profile[st - prog->statements]++;
13 #endif
14
15                         switch (st->op)
16                         {
17                         case OP_ADD_F:
18                                 OPC->_float = OPA->_float + OPB->_float;
19                                 break;
20                         case OP_ADD_V:
21                                 OPC->vector[0] = OPA->vector[0] + OPB->vector[0];
22                                 OPC->vector[1] = OPA->vector[1] + OPB->vector[1];
23                                 OPC->vector[2] = OPA->vector[2] + OPB->vector[2];
24                                 break;
25                         case OP_SUB_F:
26                                 OPC->_float = OPA->_float - OPB->_float;
27                                 break;
28                         case OP_SUB_V:
29                                 OPC->vector[0] = OPA->vector[0] - OPB->vector[0];
30                                 OPC->vector[1] = OPA->vector[1] - OPB->vector[1];
31                                 OPC->vector[2] = OPA->vector[2] - OPB->vector[2];
32                                 break;
33                         case OP_MUL_F:
34                                 OPC->_float = OPA->_float * OPB->_float;
35                                 break;
36                         case OP_MUL_V:
37                                 OPC->_float = OPA->vector[0]*OPB->vector[0] + OPA->vector[1]*OPB->vector[1] + OPA->vector[2]*OPB->vector[2];
38                                 break;
39                         case OP_MUL_FV:
40                                 OPC->vector[0] = OPA->_float * OPB->vector[0];
41                                 OPC->vector[1] = OPA->_float * OPB->vector[1];
42                                 OPC->vector[2] = OPA->_float * OPB->vector[2];
43                                 break;
44                         case OP_MUL_VF:
45                                 OPC->vector[0] = OPB->_float * OPA->vector[0];
46                                 OPC->vector[1] = OPB->_float * OPA->vector[1];
47                                 OPC->vector[2] = OPB->_float * OPA->vector[2];
48                                 break;
49                         case OP_DIV_F:
50                                 OPC->_float = OPA->_float / OPB->_float;
51                                 break;
52                         case OP_BITAND:
53                                 OPC->_float = (int)OPA->_float & (int)OPB->_float;
54                                 break;
55                         case OP_BITOR:
56                                 OPC->_float = (int)OPA->_float | (int)OPB->_float;
57                                 break;
58                         case OP_GE:
59                                 OPC->_float = OPA->_float >= OPB->_float;
60                                 break;
61                         case OP_LE:
62                                 OPC->_float = OPA->_float <= OPB->_float;
63                                 break;
64                         case OP_GT:
65                                 OPC->_float = OPA->_float > OPB->_float;
66                                 break;
67                         case OP_LT:
68                                 OPC->_float = OPA->_float < OPB->_float;
69                                 break;
70                         case OP_AND:
71                                 OPC->_float = OPA->_float && OPB->_float;
72                                 break;
73                         case OP_OR:
74                                 OPC->_float = OPA->_float || OPB->_float;
75                                 break;
76                         case OP_NOT_F:
77                                 OPC->_float = !OPA->_float;
78                                 break;
79                         case OP_NOT_V:
80                                 OPC->_float = !OPA->vector[0] && !OPA->vector[1] && !OPA->vector[2];
81                                 break;
82                         case OP_NOT_S:
83                                 OPC->_float = !OPA->string || !*PRVM_GetString(OPA->string);
84                                 break;
85                         case OP_NOT_FNC:
86                                 OPC->_float = !OPA->function;
87                                 break;
88                         case OP_NOT_ENT:
89                                 OPC->_float = (OPA->edict == 0);
90                                 break;
91                         case OP_EQ_F:
92                                 OPC->_float = OPA->_float == OPB->_float;
93                                 break;
94                         case OP_EQ_V:
95                                 OPC->_float = (OPA->vector[0] == OPB->vector[0]) && (OPA->vector[1] == OPB->vector[1]) && (OPA->vector[2] == OPB->vector[2]);
96                                 break;
97                         case OP_EQ_S:
98                                 OPC->_float = !strcmp(PRVM_GetString(OPA->string),PRVM_GetString(OPB->string));
99                                 break;
100                         case OP_EQ_E:
101                                 OPC->_float = OPA->_int == OPB->_int;
102                                 break;
103                         case OP_EQ_FNC:
104                                 OPC->_float = OPA->function == OPB->function;
105                                 break;
106                         case OP_NE_F:
107                                 OPC->_float = OPA->_float != OPB->_float;
108                                 break;
109                         case OP_NE_V:
110                                 OPC->_float = (OPA->vector[0] != OPB->vector[0]) || (OPA->vector[1] != OPB->vector[1]) || (OPA->vector[2] != OPB->vector[2]);
111                                 break;
112                         case OP_NE_S:
113                                 OPC->_float = strcmp(PRVM_GetString(OPA->string),PRVM_GetString(OPB->string));
114                                 break;
115                         case OP_NE_E:
116                                 OPC->_float = OPA->_int != OPB->_int;
117                                 break;
118                         case OP_NE_FNC:
119                                 OPC->_float = OPA->function != OPB->function;
120                                 break;
121
122                 //==================
123                         case OP_STORE_F:
124                         case OP_STORE_ENT:
125                         case OP_STORE_FLD:              // integers
126                         case OP_STORE_S:
127                         case OP_STORE_FNC:              // pointers
128                                 OPB->_int = OPA->_int;
129                                 break;
130                         case OP_STORE_V:
131                                 OPB->ivector[0] = OPA->ivector[0];
132                                 OPB->ivector[1] = OPA->ivector[1];
133                                 OPB->ivector[2] = OPA->ivector[2];
134                                 break;
135
136                         case OP_STOREP_F:
137                         case OP_STOREP_ENT:
138                         case OP_STOREP_FLD:             // integers
139                         case OP_STOREP_S:
140                         case OP_STOREP_FNC:             // pointers
141 #if PRVMBOUNDSCHECK
142                                 if (OPB->_int < 0 || OPB->_int + 4 > prog->edictareasize)
143                                 {
144                                         prog->xfunction->profile += (st - startst);
145                                         prog->xstatement = st - prog->statements;
146                                         PRVM_ERROR("%s attempted to write to an out of bounds edict (%i)", PRVM_NAME, OPB->_int);
147                                         return;
148                                 }
149 #endif
150                                 ptr = (prvm_eval_t *)((unsigned char *)prog->edictsfields + OPB->_int);
151                                 ptr->_int = OPA->_int;
152                                 break;
153                         case OP_STOREP_V:
154 #if PRVMBOUNDSCHECK
155                                 if (OPB->_int < 0 || OPB->_int + 12 > prog->edictareasize)
156                                 {
157                                         prog->xfunction->profile += (st - startst);
158                                         prog->xstatement = st - prog->statements;
159                                         PRVM_ERROR("%s attempted to write to an out of bounds edict (%i)", PRVM_NAME, OPB->_int);
160                                         return;
161                                 }
162 #endif
163                                 ptr = (prvm_eval_t *)((unsigned char *)prog->edictsfields + OPB->_int);
164                                 ptr->vector[0] = OPA->vector[0];
165                                 ptr->vector[1] = OPA->vector[1];
166                                 ptr->vector[2] = OPA->vector[2];
167                                 break;
168
169                         case OP_ADDRESS:
170 #if PRVMBOUNDSCHECK
171                                 if ((unsigned int)(OPB->_int) >= (unsigned int)(prog->progs->entityfields))
172                                 {
173                                         prog->xfunction->profile += (st - startst);
174                                         prog->xstatement = st - prog->statements;
175                                         PRVM_ERROR("%s attempted to address an invalid field (%i) in an edict", PRVM_NAME, OPB->_int);
176                                         return;
177                                 }
178 #endif
179                                 if (OPA->edict == 0 && !prog->allowworldwrites)
180                                 {
181                                         prog->xfunction->profile += (st - startst);
182                                         prog->xstatement = st - prog->statements;
183                                         PRVM_ERROR("forbidden assignment to null/world entity in %s", PRVM_NAME);
184                                         return;
185                                 }
186                                 ed = PRVM_PROG_TO_EDICT(OPA->edict);
187                                 OPC->_int = (unsigned char *)((int *)ed->fields.vp + OPB->_int) - (unsigned char *)prog->edictsfields;
188                                 break;
189
190                         case OP_LOAD_F:
191                         case OP_LOAD_FLD:
192                         case OP_LOAD_ENT:
193                         case OP_LOAD_S:
194                         case OP_LOAD_FNC:
195 #if PRVMBOUNDSCHECK
196                                 if ((unsigned int)(OPB->_int) >= (unsigned int)(prog->progs->entityfields))
197                                 {
198                                         prog->xfunction->profile += (st - startst);
199                                         prog->xstatement = st - prog->statements;
200                                         PRVM_ERROR("%s attempted to read an invalid field in an edict (%i)", PRVM_NAME, OPB->_int);
201                                         return;
202                                 }
203 #endif
204                                 ed = PRVM_PROG_TO_EDICT(OPA->edict);
205                                 OPC->_int = ((prvm_eval_t *)((int *)ed->fields.vp + OPB->_int))->_int;
206                                 break;
207
208                         case OP_LOAD_V:
209 #if PRVMBOUNDSCHECK
210                                 if (OPB->_int < 0 || OPB->_int + 2 >= prog->progs->entityfields)
211                                 {
212                                         prog->xfunction->profile += (st - startst);
213                                         prog->xstatement = st - prog->statements;
214                                         PRVM_ERROR("%s attempted to read an invalid field in an edict (%i)", PRVM_NAME, OPB->_int);
215                                         return;
216                                 }
217 #endif
218                                 ed = PRVM_PROG_TO_EDICT(OPA->edict);
219                                 OPC->vector[0] = ((prvm_eval_t *)((int *)ed->fields.vp + OPB->_int))->vector[0];
220                                 OPC->vector[1] = ((prvm_eval_t *)((int *)ed->fields.vp + OPB->_int))->vector[1];
221                                 OPC->vector[2] = ((prvm_eval_t *)((int *)ed->fields.vp + OPB->_int))->vector[2];
222                                 break;
223
224                 //==================
225
226                         case OP_IFNOT:
227                                 if (!OPA->_int)
228                                 {
229                                         prog->xfunction->profile += (st - startst);
230                                         st += st->b - 1;        // offset the s++
231                                         startst = st;
232                                         if (++jumpcount == 10000000)
233                                         {
234                                                 prog->xstatement = st - prog->statements;
235                                                 PRVM_Profile(1<<30, 1000000);
236                                                 PRVM_ERROR("runaway loop counter hit limit of %d jumps\ntip: read above for list of most-executed functions", jumpcount, PRVM_NAME);
237                                         }
238                                 }
239                                 break;
240
241                         case OP_IF:
242                                 if (OPA->_int)
243                                 {
244                                         prog->xfunction->profile += (st - startst);
245                                         st += st->b - 1;        // offset the s++
246                                         startst = st;
247                                         if (++jumpcount == 10000000)
248                                         {
249                                                 prog->xstatement = st - prog->statements;
250                                                 PRVM_Profile(1<<30, 1000000);
251                                                 PRVM_ERROR("runaway loop counter hit limit of %d jumps\ntip: read above for list of most-executed functions", jumpcount, PRVM_NAME);
252                                         }
253                                 }
254                                 break;
255
256                         case OP_GOTO:
257                                 prog->xfunction->profile += (st - startst);
258                                 st += st->a - 1;        // offset the s++
259                                 startst = st;
260                                 if (++jumpcount == 10000000)
261                                 {
262                                         prog->xstatement = st - prog->statements;
263                                         PRVM_Profile(1<<30, 1000000);
264                                         PRVM_ERROR("runaway loop counter hit limit of %d jumps\ntip: read above for list of most-executed functions", jumpcount, PRVM_NAME);
265                                 }
266                                 break;
267
268                         case OP_CALL0:
269                         case OP_CALL1:
270                         case OP_CALL2:
271                         case OP_CALL3:
272                         case OP_CALL4:
273                         case OP_CALL5:
274                         case OP_CALL6:
275                         case OP_CALL7:
276                         case OP_CALL8:
277                                 prog->xfunction->profile += (st - startst);
278                                 startst = st;
279                                 prog->xstatement = st - prog->statements;
280                                 prog->argc = st->op - OP_CALL0;
281                                 if (!OPA->function)
282                                         PRVM_ERROR("NULL function in %s", PRVM_NAME);
283
284                                 newf = &prog->functions[OPA->function];
285                                 newf->callcount++;
286
287                                 if (newf->first_statement < 0)
288                                 {
289                                         // negative statements are built in functions
290                                         int builtinnumber = -newf->first_statement;
291                                         prog->xfunction->builtinsprofile++;
292                                         if (builtinnumber < prog->numbuiltins && prog->builtins[builtinnumber])
293                                                 prog->builtins[builtinnumber]();
294                                         else
295                                                 PRVM_ERROR("No such builtin #%i in %s", builtinnumber, PRVM_NAME);
296                                 }
297                                 else
298                                         st = prog->statements + PRVM_EnterFunction(newf);
299                                 startst = st;
300                                 break;
301
302                         case OP_DONE:
303                         case OP_RETURN:
304                                 prog->xfunction->profile += (st - startst);
305                                 prog->xstatement = st - prog->statements;
306
307                                 prog->globals.generic[OFS_RETURN] = prog->globals.generic[(unsigned short) st->a];
308                                 prog->globals.generic[OFS_RETURN+1] = prog->globals.generic[(unsigned short) st->a+1];
309                                 prog->globals.generic[OFS_RETURN+2] = prog->globals.generic[(unsigned short) st->a+2];
310
311                                 st = prog->statements + PRVM_LeaveFunction();
312                                 startst = st;
313                                 if (prog->depth <= exitdepth)
314                                         return;         // all done
315                                 if (prog->trace != cachedpr_trace)
316                                         goto chooseexecprogram;
317                                 break;
318
319                         case OP_STATE:
320                                 if(prog->flag & PRVM_OP_STATE)
321                                 {
322                                         ed = PRVM_PROG_TO_EDICT(PRVM_G_INT(prog->self->ofs));
323                                         PRVM_E_FLOAT(ed,PRVM_ED_FindField ("nextthink")->ofs) = *prog->time + 0.1;
324                                         PRVM_E_FLOAT(ed,PRVM_ED_FindField ("frame")->ofs) = OPA->_float;
325                                         *(func_t *)((float*)ed->fields.vp + PRVM_ED_FindField ("think")->ofs) = OPB->function;
326                                 }
327                                 else
328                                 {
329                                         prog->xfunction->profile += (st - startst);
330                                         prog->xstatement = st - prog->statements;
331                                         PRVM_ERROR("OP_STATE not supported by %s", PRVM_NAME);
332                                 }
333                                 break;
334
335 // LordHavoc: to be enabled when Progs version 7 (or whatever it will be numbered) is finalized
336 /*
337                         case OP_ADD_I:
338                                 OPC->_int = OPA->_int + OPB->_int;
339                                 break;
340                         case OP_ADD_IF:
341                                 OPC->_int = OPA->_int + (int) OPB->_float;
342                                 break;
343                         case OP_ADD_FI:
344                                 OPC->_float = OPA->_float + (float) OPB->_int;
345                                 break;
346                         case OP_SUB_I:
347                                 OPC->_int = OPA->_int - OPB->_int;
348                                 break;
349                         case OP_SUB_IF:
350                                 OPC->_int = OPA->_int - (int) OPB->_float;
351                                 break;
352                         case OP_SUB_FI:
353                                 OPC->_float = OPA->_float - (float) OPB->_int;
354                                 break;
355                         case OP_MUL_I:
356                                 OPC->_int = OPA->_int * OPB->_int;
357                                 break;
358                         case OP_MUL_IF:
359                                 OPC->_int = OPA->_int * (int) OPB->_float;
360                                 break;
361                         case OP_MUL_FI:
362                                 OPC->_float = OPA->_float * (float) OPB->_int;
363                                 break;
364                         case OP_MUL_VI:
365                                 OPC->vector[0] = (float) OPB->_int * OPA->vector[0];
366                                 OPC->vector[1] = (float) OPB->_int * OPA->vector[1];
367                                 OPC->vector[2] = (float) OPB->_int * OPA->vector[2];
368                                 break;
369                         case OP_DIV_VF:
370                                 {
371                                         float temp = 1.0f / OPB->_float;
372                                         OPC->vector[0] = temp * OPA->vector[0];
373                                         OPC->vector[1] = temp * OPA->vector[1];
374                                         OPC->vector[2] = temp * OPA->vector[2];
375                                 }
376                                 break;
377                         case OP_DIV_I:
378                                 OPC->_int = OPA->_int / OPB->_int;
379                                 break;
380                         case OP_DIV_IF:
381                                 OPC->_int = OPA->_int / (int) OPB->_float;
382                                 break;
383                         case OP_DIV_FI:
384                                 OPC->_float = OPA->_float / (float) OPB->_int;
385                                 break;
386                         case OP_CONV_IF:
387                                 OPC->_float = OPA->_int;
388                                 break;
389                         case OP_CONV_FI:
390                                 OPC->_int = OPA->_float;
391                                 break;
392                         case OP_BITAND_I:
393                                 OPC->_int = OPA->_int & OPB->_int;
394                                 break;
395                         case OP_BITOR_I:
396                                 OPC->_int = OPA->_int | OPB->_int;
397                                 break;
398                         case OP_BITAND_IF:
399                                 OPC->_int = OPA->_int & (int)OPB->_float;
400                                 break;
401                         case OP_BITOR_IF:
402                                 OPC->_int = OPA->_int | (int)OPB->_float;
403                                 break;
404                         case OP_BITAND_FI:
405                                 OPC->_float = (int)OPA->_float & OPB->_int;
406                                 break;
407                         case OP_BITOR_FI:
408                                 OPC->_float = (int)OPA->_float | OPB->_int;
409                                 break;
410                         case OP_GE_I:
411                                 OPC->_float = OPA->_int >= OPB->_int;
412                                 break;
413                         case OP_LE_I:
414                                 OPC->_float = OPA->_int <= OPB->_int;
415                                 break;
416                         case OP_GT_I:
417                                 OPC->_float = OPA->_int > OPB->_int;
418                                 break;
419                         case OP_LT_I:
420                                 OPC->_float = OPA->_int < OPB->_int;
421                                 break;
422                         case OP_AND_I:
423                                 OPC->_float = OPA->_int && OPB->_int;
424                                 break;
425                         case OP_OR_I:
426                                 OPC->_float = OPA->_int || OPB->_int;
427                                 break;
428                         case OP_GE_IF:
429                                 OPC->_float = (float)OPA->_int >= OPB->_float;
430                                 break;
431                         case OP_LE_IF:
432                                 OPC->_float = (float)OPA->_int <= OPB->_float;
433                                 break;
434                         case OP_GT_IF:
435                                 OPC->_float = (float)OPA->_int > OPB->_float;
436                                 break;
437                         case OP_LT_IF:
438                                 OPC->_float = (float)OPA->_int < OPB->_float;
439                                 break;
440                         case OP_AND_IF:
441                                 OPC->_float = (float)OPA->_int && OPB->_float;
442                                 break;
443                         case OP_OR_IF:
444                                 OPC->_float = (float)OPA->_int || OPB->_float;
445                                 break;
446                         case OP_GE_FI:
447                                 OPC->_float = OPA->_float >= (float)OPB->_int;
448                                 break;
449                         case OP_LE_FI:
450                                 OPC->_float = OPA->_float <= (float)OPB->_int;
451                                 break;
452                         case OP_GT_FI:
453                                 OPC->_float = OPA->_float > (float)OPB->_int;
454                                 break;
455                         case OP_LT_FI:
456                                 OPC->_float = OPA->_float < (float)OPB->_int;
457                                 break;
458                         case OP_AND_FI:
459                                 OPC->_float = OPA->_float && (float)OPB->_int;
460                                 break;
461                         case OP_OR_FI:
462                                 OPC->_float = OPA->_float || (float)OPB->_int;
463                                 break;
464                         case OP_NOT_I:
465                                 OPC->_float = !OPA->_int;
466                                 break;
467                         case OP_EQ_I:
468                                 OPC->_float = OPA->_int == OPB->_int;
469                                 break;
470                         case OP_EQ_IF:
471                                 OPC->_float = (float)OPA->_int == OPB->_float;
472                                 break;
473                         case OP_EQ_FI:
474                                 OPC->_float = OPA->_float == (float)OPB->_int;
475                                 break;
476                         case OP_NE_I:
477                                 OPC->_float = OPA->_int != OPB->_int;
478                                 break;
479                         case OP_NE_IF:
480                                 OPC->_float = (float)OPA->_int != OPB->_float;
481                                 break;
482                         case OP_NE_FI:
483                                 OPC->_float = OPA->_float != (float)OPB->_int;
484                                 break;
485                         case OP_STORE_I:
486                                 OPB->_int = OPA->_int;
487                                 break;
488                         case OP_STOREP_I:
489 #if PRBOUNDSCHECK
490                                 if (OPB->_int < 0 || OPB->_int + 4 > pr_edictareasize)
491                                 {
492                                         prog->xfunction->profile += (st - startst);
493                                         prog->xstatement = st - prog->statements;
494                                         PRVM_ERROR ("%s Progs attempted to write to an out of bounds edict", PRVM_NAME);
495                                         return;
496                                 }
497 #endif
498                                 ptr = (prvm_eval_t *)((unsigned char *)prog->edictsfields + OPB->_int);
499                                 ptr->_int = OPA->_int;
500                                 break;
501                         case OP_LOAD_I:
502 #if PRBOUNDSCHECK
503                                 if (OPA->edict < 0 || OPA->edict >= pr_edictareasize)
504                                 {
505                                         prog->xfunction->profile += (st - startst);
506                                         prog->xstatement = st - prog->statements;
507                                         PRVM_ERROR ("%s Progs attempted to read an out of bounds edict number", PRVM_NAME);
508                                         return;
509                                 }
510                                 if (OPB->_int < 0 || OPB->_int >= progs->entityfields)
511                                 {
512                                         prog->xfunction->profile += (st - startst);
513                                         prog->xstatement = st - prog->statements;
514                                         PRVM_ERROR ("%s Progs attempted to read an invalid field in an edict", PRVM_NAME);
515                                         return;
516                                 }
517 #endif
518                                 ed = PRVM_PROG_TO_EDICT(OPA->edict);
519                                 OPC->_int = ((prvm_eval_t *)((int *)ed->v + OPB->_int))->_int;
520                                 break;
521
522                         case OP_GSTOREP_I:
523                         case OP_GSTOREP_F:
524                         case OP_GSTOREP_ENT:
525                         case OP_GSTOREP_FLD:            // integers
526                         case OP_GSTOREP_S:
527                         case OP_GSTOREP_FNC:            // pointers
528 #if PRBOUNDSCHECK
529                                 if (OPB->_int < 0 || OPB->_int >= pr_globaldefs)
530                                 {
531                                         prog->xfunction->profile += (st - startst);
532                                         prog->xstatement = st - prog->statements;
533                                         PRVM_ERROR ("%s Progs attempted to write to an invalid indexed global", PRVM_NAME);
534                                         return;
535                                 }
536 #endif
537                                 pr_globals[OPB->_int] = OPA->_float;
538                                 break;
539                         case OP_GSTOREP_V:
540 #if PRBOUNDSCHECK
541                                 if (OPB->_int < 0 || OPB->_int + 2 >= pr_globaldefs)
542                                 {
543                                         prog->xfunction->profile += (st - startst);
544                                         prog->xstatement = st - prog->statements;
545                                         PRVM_ERROR ("%s Progs attempted to write to an invalid indexed global", PRVM_NAME);
546                                         return;
547                                 }
548 #endif
549                                 pr_globals[OPB->_int  ] = OPA->vector[0];
550                                 pr_globals[OPB->_int+1] = OPA->vector[1];
551                                 pr_globals[OPB->_int+2] = OPA->vector[2];
552                                 break;
553
554                         case OP_GADDRESS:
555                                 i = OPA->_int + (int) OPB->_float;
556 #if PRBOUNDSCHECK
557                                 if (i < 0 || i >= pr_globaldefs)
558                                 {
559                                         prog->xfunction->profile += (st - startst);
560                                         prog->xstatement = st - prog->statements;
561                                         PRVM_ERROR ("%s Progs attempted to address an out of bounds global", PRVM_NAME);
562                                         return;
563                                 }
564 #endif
565                                 OPC->_float = pr_globals[i];
566                                 break;
567
568                         case OP_GLOAD_I:
569                         case OP_GLOAD_F:
570                         case OP_GLOAD_FLD:
571                         case OP_GLOAD_ENT:
572                         case OP_GLOAD_S:
573                         case OP_GLOAD_FNC:
574 #if PRBOUNDSCHECK
575                                 if (OPA->_int < 0 || OPA->_int >= pr_globaldefs)
576                                 {
577                                         prog->xfunction->profile += (st - startst);
578                                         prog->xstatement = st - prog->statements;
579                                         PRVM_ERROR ("%s Progs attempted to read an invalid indexed global", PRVM_NAME);
580                                         return;
581                                 }
582 #endif
583                                 OPC->_float = pr_globals[OPA->_int];
584                                 break;
585
586                         case OP_GLOAD_V:
587 #if PRBOUNDSCHECK
588                                 if (OPA->_int < 0 || OPA->_int + 2 >= pr_globaldefs)
589                                 {
590                                         prog->xfunction->profile += (st - startst);
591                                         prog->xstatement = st - prog->statements;
592                                         PRVM_ERROR ("%s Progs attempted to read an invalid indexed global", PRVM_NAME);
593                                         return;
594                                 }
595 #endif
596                                 OPC->vector[0] = pr_globals[OPA->_int  ];
597                                 OPC->vector[1] = pr_globals[OPA->_int+1];
598                                 OPC->vector[2] = pr_globals[OPA->_int+2];
599                                 break;
600
601                         case OP_BOUNDCHECK:
602                                 if (OPA->_int < 0 || OPA->_int >= st->b)
603                                 {
604                                         prog->xfunction->profile += (st - startst);
605                                         prog->xstatement = st - prog->statements;
606                                         PRVM_ERROR ("%s Progs boundcheck failed at line number %d, value is < 0 or >= %d", PRVM_NAME, st->b, st->c);
607                                         return;
608                                 }
609                                 break;
610
611 */
612
613                         default:
614                                 prog->xfunction->profile += (st - startst);
615                                 prog->xstatement = st - prog->statements;
616                                 PRVM_ERROR ("Bad opcode %i in %s", st->op, PRVM_NAME);
617                         }
618                 }
619