2 //we have two conditions.
3 //one allows us to debug and trace through our code, the other doesn't.
5 //hopefully, the compiler will do a great job at optimising this code for us, where required.
6 //if it dosn't, then bum.
8 //the general overhead should be reduced significantly, and I would be supprised if it did run slower.
10 //run away loops are checked for ONLY on gotos and function calls. This might give a poorer check, but it will run faster overall.
12 //Appears to work fine.
16 #define reeval reeval16
18 #define pr_statements pr_statements16
19 #define fakeop fakeop16
20 #define dstatement_t dstatement16_t
21 #define sofs signed short
22 #define uofs unsigned short
25 #define reeval reeval32
27 #define pr_statements pr_statements32
28 #define fakeop fakeop32
29 #define dstatement_t dstatement32_t
30 #define sofs signed int
31 #define uofs unsigned int
33 #error INTSIZE should be set to 32.
38 #define ENGINEPOINTER(p) ((char*)(p) - progfuncs->stringtable)
39 #define QCPOINTER(p) (eval_t *)(p->_int+progfuncs->stringtable)
40 #define QCPOINTERM(p) (eval_t *)((p)+progfuncs->stringtable)
45 cont: //last statement may have been a breakpoint
48 s=ShowStep(progfuncs, s);
49 st = pr_statements + s;
52 switch (st->op & ~0x8000)
59 OPC->_float = OPA->_float + OPB->_float;
62 OPC->_vector[0] = OPA->_vector[0] + OPB->_vector[0];
63 OPC->_vector[1] = OPA->_vector[1] + OPB->_vector[1];
64 OPC->_vector[2] = OPA->_vector[2] + OPB->_vector[2];
68 OPC->_float = OPA->_float - OPB->_float;
71 OPC->_vector[0] = OPA->_vector[0] - OPB->_vector[0];
72 OPC->_vector[1] = OPA->_vector[1] - OPB->_vector[1];
73 OPC->_vector[2] = OPA->_vector[2] - OPB->_vector[2];
77 OPC->_float = OPA->_float * OPB->_float;
80 OPC->_float = OPA->_vector[0]*OPB->_vector[0]
81 + OPA->_vector[1]*OPB->_vector[1]
82 + OPA->_vector[2]*OPB->_vector[2];
85 OPC->_vector[0] = OPA->_float * OPB->_vector[0];
86 OPC->_vector[1] = OPA->_float * OPB->_vector[1];
87 OPC->_vector[2] = OPA->_float * OPB->_vector[2];
90 OPC->_vector[0] = OPB->_float * OPA->_vector[0];
91 OPC->_vector[1] = OPB->_float * OPA->_vector[1];
92 OPC->_vector[2] = OPB->_float * OPA->_vector[2];
96 OPC->_float = OPA->_float / OPB->_float;
99 OPC->_vector[0] = OPB->_float / OPA->_vector[0];
100 OPC->_vector[1] = OPB->_float / OPA->_vector[1];
101 OPC->_vector[2] = OPB->_float / OPA->_vector[2];
105 OPC->_float = (float)((int)OPA->_float & (int)OPB->_float);
109 OPC->_float = (float)((int)OPA->_float | (int)OPB->_float);
114 OPC->_float = (float)(OPA->_float >= OPB->_float);
117 OPC->_int = (int)(OPA->_int >= OPB->_int);
120 OPC->_float = (float)(OPA->_int >= OPB->_float);
123 OPC->_float = (float)(OPA->_float >= OPB->_int);
127 OPC->_float = (float)(OPA->_float <= OPB->_float);
130 OPC->_int = (int)(OPA->_int <= OPB->_int);
133 OPC->_float = (float)(OPA->_int <= OPB->_float);
136 OPC->_float = (float)(OPA->_float <= OPB->_int);
140 OPC->_float = (float)(OPA->_float > OPB->_float);
143 OPC->_int = (int)(OPA->_int > OPB->_int);
146 OPC->_float = (float)(OPA->_int > OPB->_float);
149 OPC->_float = (float)(OPA->_float > OPB->_int);
153 OPC->_float = (float)(OPA->_float < OPB->_float);
156 OPC->_int = (int)(OPA->_int < OPB->_int);
159 OPC->_float = (float)(OPA->_int < OPB->_float);
162 OPC->_float = (float)(OPA->_float < OPB->_int);
166 OPC->_float = (float)(OPA->_float && OPB->_float);
169 OPC->_float = (float)(OPA->_float || OPB->_float);
173 OPC->_float = (float)(!OPA->_float);
176 OPC->_float = (float)(!OPA->_vector[0] && !OPA->_vector[1] && !OPA->_vector[2]);
179 OPC->_float = (float)(!(OPA->string) || !*PR_StringToNative(progfuncs, OPA->string));
182 OPC->_float = (float)(!(OPA->function & ~0xff000000));
185 OPC->_float = (float)(PROG_TO_EDICT(progfuncs, OPA->edict) == (edictrun_t *)sv_edicts);
189 OPC->_float = (float)(OPA->_float == OPB->_float);
192 OPC->_float = (float)(OPA->_int == OPB->_float);
195 OPC->_float = (float)(OPA->_float == OPB->_int);
200 OPC->_float = (float)((OPA->_vector[0] == OPB->_vector[0]) &&
201 (OPA->_vector[1] == OPB->_vector[1]) &&
202 (OPA->_vector[2] == OPB->_vector[2]));
205 if (OPA->string==OPB->string)
207 else if (!OPA->string)
209 if (!OPB->string || !*PR_StringToNative(progfuncs, OPB->string))
214 else if (!OPB->string)
216 if (!OPA->string || !*PR_StringToNative(progfuncs, OPA->string))
222 OPC->_float = (float)(!strcmp(PR_StringToNative(progfuncs, OPA->string),PR_StringToNative(progfuncs, OPB->string)));
225 OPC->_float = (float)(OPA->_int == OPB->_int);
228 OPC->_float = (float)(OPA->function == OPB->function);
233 OPC->_float = (float)(OPA->_float != OPB->_float);
236 OPC->_float = (float)((OPA->_vector[0] != OPB->_vector[0]) ||
237 (OPA->_vector[1] != OPB->_vector[1]) ||
238 (OPA->_vector[2] != OPB->_vector[2]));
241 if (OPA->string==OPB->string)
243 else if (!OPA->string)
245 if (!OPB->string || !*(PR_StringToNative(progfuncs, OPB->string)))
250 else if (!OPB->string)
252 if (!OPA->string || !*PR_StringToNative(progfuncs, OPA->string))
258 OPC->_float = (float)(strcmp(PR_StringToNative(progfuncs, OPA->string),PR_StringToNative(progfuncs, OPB->string)));
261 OPC->_float = (float)(OPA->_int != OPB->_int);
264 OPC->_float = (float)(OPA->function != OPB->function);
269 OPB->_float = (float)OPA->_int;
272 OPB->_int = (int)OPA->_float;
277 case OP_STORE_FLD: // integers
280 case OP_STORE_FNC: // pointers
282 OPB->_int = OPA->_int;
285 OPB->_vector[0] = OPA->_vector[0];
286 OPB->_vector[1] = OPA->_vector[1];
287 OPB->_vector[2] = OPA->_vector[2];
290 //store a value to a pointer
292 if ((unsigned int)OPB->_int >= addressableused)
294 pr_xstatement = st-pr_statements;
295 PR_RunError (progfuncs, "bad pointer write in %s", progfuncs->stringtable + pr_xfunction->s_name);
297 ptr = QCPOINTER(OPB);
298 ptr->_float = (float)OPA->_int;
301 if ((unsigned int)OPB->_int >= addressableused)
303 pr_xstatement = st-pr_statements;
304 PR_RunError (progfuncs, "bad pointer write in %s", progfuncs->stringtable + pr_xfunction->s_name);
306 ptr = QCPOINTER(OPB);
307 ptr->_int = (int)OPA->_float;
310 if ((unsigned int)OPB->_int >= addressableused)
312 pr_xstatement = st-pr_statements;
313 PR_RunError (progfuncs, "bad pointer write in %s", progfuncs->stringtable + pr_xfunction->s_name);
315 ptr = QCPOINTER(OPB);
316 ptr->_int = OPA->_int;
320 case OP_STOREP_FLD: // integers
322 case OP_STOREP_FNC: // pointers
323 if ((unsigned int)OPB->_int >= addressableused)
325 pr_xstatement = st-pr_statements;
326 PR_RunError (progfuncs, "bad pointer write in %s", progfuncs->stringtable + pr_xfunction->s_name);
328 ptr = QCPOINTER(OPB);
329 ptr->_int = OPA->_int;
332 if ((unsigned int)OPB->_int >= addressableused)
334 pr_xstatement = st-pr_statements;
335 PR_RunError (progfuncs, "bad pointer write in %s", progfuncs->stringtable + pr_xfunction->s_name);
337 ptr = QCPOINTER(OPB);
338 ptr->_vector[0] = OPA->_vector[0];
339 ptr->_vector[1] = OPA->_vector[1];
340 ptr->_vector[2] = OPA->_vector[2];
343 case OP_STOREP_C: //store character in a string
344 if ((unsigned int)OPB->_int >= addressableused)
346 pr_xstatement = st-pr_statements;
347 PR_RunError (progfuncs, "bad pointer write in %s", progfuncs->stringtable + pr_xfunction->s_name);
349 ptr = QCPOINTER(OPB);
350 *(unsigned char *)ptr = (char)OPA->_float;
353 case OP_MULSTORE_F: // f *= f
354 OPB->_float *= OPA->_float;
356 case OP_MULSTORE_V: // v *= f
357 OPB->_vector[0] *= OPA->_float;
358 OPB->_vector[1] *= OPA->_float;
359 OPB->_vector[2] *= OPA->_float;
361 case OP_MULSTOREP_F: // e.f *= f
362 if ((unsigned int)OPB->_int >= addressableused)
364 pr_xstatement = st-pr_statements;
365 PR_RunError (progfuncs, "bad pointer write in %s", progfuncs->stringtable + pr_xfunction->s_name);
367 ptr = QCPOINTER(OPB);
368 OPC->_float = (ptr->_float *= OPA->_float);
370 case OP_MULSTOREP_V: // e.v *= f
371 ptr = QCPOINTER(OPB);
372 OPC->_vector[0] = (ptr->_vector[0] *= OPA->_float);
373 OPC->_vector[0] = (ptr->_vector[1] *= OPA->_float);
374 OPC->_vector[0] = (ptr->_vector[2] *= OPA->_float);
377 case OP_DIVSTORE_F: // f /= f
378 OPB->_float /= OPA->_float;
380 case OP_DIVSTOREP_F: // e.f /= f
381 ptr = QCPOINTER(OPB);
382 OPC->_float = (ptr->_float /= OPA->_float);
385 case OP_ADDSTORE_F: // f += f
386 OPB->_float += OPA->_float;
388 case OP_ADDSTORE_V: // v += v
389 OPB->_vector[0] += OPA->_vector[0];
390 OPB->_vector[1] += OPA->_vector[1];
391 OPB->_vector[2] += OPA->_vector[2];
393 case OP_ADDSTOREP_F: // e.f += f
394 ptr = QCPOINTER(OPB);
395 OPC->_float = (ptr->_float += OPA->_float);
397 case OP_ADDSTOREP_V: // e.v += v
398 ptr = QCPOINTER(OPB);
399 OPC->_vector[0] = (ptr->_vector[0] += OPA->_vector[0]);
400 OPC->_vector[1] = (ptr->_vector[1] += OPA->_vector[1]);
401 OPC->_vector[2] = (ptr->_vector[2] += OPA->_vector[2]);
404 case OP_SUBSTORE_F: // f -= f
405 OPB->_float -= OPA->_float;
407 case OP_SUBSTORE_V: // v -= v
408 OPB->_vector[0] -= OPA->_vector[0];
409 OPB->_vector[1] -= OPA->_vector[1];
410 OPB->_vector[2] -= OPA->_vector[2];
412 case OP_SUBSTOREP_F: // e.f -= f
413 ptr = QCPOINTER(OPB);
414 OPC->_float = (ptr->_float -= OPA->_float);
416 case OP_SUBSTOREP_V: // e.v -= v
417 ptr = QCPOINTER(OPB);
418 OPC->_vector[0] = (ptr->_vector[0] -= OPA->_vector[0]);
419 OPC->_vector[1] = (ptr->_vector[1] -= OPA->_vector[1]);
420 OPC->_vector[2] = (ptr->_vector[2] -= OPA->_vector[2]);
424 //get a pointer to a field var
426 if ((unsigned)OPA->edict >= (unsigned)maxedicts)
430 printf("OP_ADDRESS references invalid entity in %s", progfuncs->stringtable + pr_xfunction->s_name);
434 PR_RunError (progfuncs, "OP_ADDRESS references invalid entity in %s", PR_StringToNative(progfuncs, pr_xfunction->s_name));
437 ed = PROG_TO_EDICT(progfuncs, OPA->edict);
439 NUM_FOR_EDICT(ed); // make sure it's in range
441 if (!ed || ed->readonly)
443 pr_xstatement = st-pr_statements;
445 //boot it over to the debugger
447 printf("assignment to read-only entity in %s", progfuncs->stringtable + pr_xfunction->s_name);
454 d16 = ED_GlobalAtOfs16(progfuncs, st->a);
455 f = ED_FieldAtOfs(progfuncs, OPB->_int + progfuncs->fieldadjust);
456 PR_RunError (progfuncs, "assignment to read-only entity in %s (%s.%s)", PR_StringToNative(progfuncs, pr_xfunction->s_name), PR_StringToNative(progfuncs, d16->s_name), f?f->name:NULL);
461 //Whilst the next block would technically be correct, we don't use it as it breaks too many quake mods.
464 // pr_xstatement = st-pr_statements;
465 // PR_RunError (progfuncs, "assignment to free entitiy in %s", progfuncs->stringtable + pr_xfunction->s_name);
467 OPC->_int = ENGINEPOINTER((((int *)edvars(ed)) + OPB->_int + progfuncs->fieldadjust));
470 //load a field to a value
477 if ((unsigned)OPA->edict >= (unsigned)maxedicts)
478 PR_RunError (progfuncs, "OP_LOAD references invalid entity in %s", progfuncs->stringtable + pr_xfunction->s_name);
479 ed = PROG_TO_EDICT(progfuncs, OPA->edict);
481 NUM_FOR_EDICT(ed); // make sure it's in range
483 ptr = (eval_t *)(((int *)edvars(ed)) + OPB->_int + progfuncs->fieldadjust);
484 OPC->_int = ptr->_int;
488 if ((unsigned)OPA->edict >= (unsigned)maxedicts)
489 PR_RunError (progfuncs, "OP_LOAD_V references invalid entity in %s", progfuncs->stringtable + pr_xfunction->s_name);
490 ed = PROG_TO_EDICT(progfuncs, OPA->edict);
492 NUM_FOR_EDICT(ed); // make sure it's in range
494 ptr = (eval_t *)(((int *)edvars(ed)) + OPB->_int + progfuncs->fieldadjust);
495 OPC->_vector[0] = ptr->_vector[0];
496 OPC->_vector[1] = ptr->_vector[1];
497 OPC->_vector[2] = ptr->_vector[2];
504 if (!OPA->string || !PR_StringToNative(progfuncs, OPA->string))
505 st += (sofs)st->b - 1; // offset the s++
511 st += (sofs)st->b - 1; // offset the s++
517 st += (sofs)st->b - 1; // offset the s++
522 if (OPA->string && PR_StringToNative(progfuncs, OPA->string))
523 st += (sofs)st->b - 1; // offset the s++
529 st += (sofs)st->b - 1; // offset the s++
535 st += (sofs)st->b - 1; // offset the s++
540 st += (sofs)st->a - 1; // offset the s++
550 G_VECTOR(OFS_PARM1)[0] = OPC->_vector[0];
551 G_VECTOR(OFS_PARM1)[1] = OPC->_vector[1];
552 G_VECTOR(OFS_PARM1)[2] = OPC->_vector[2];
554 G_VECTOR(OFS_PARM0)[0] = OPB->_vector[0];
555 G_VECTOR(OFS_PARM0)[1] = OPB->_vector[1];
556 G_VECTOR(OFS_PARM0)[2] = OPB->_vector[2];
568 pr_xstatement = st-pr_statements;
571 if (st->op > OP_CALL8)
572 pr_argc = st->op - (OP_CALL1H-1);
574 pr_argc = st->op - OP_CALL0;
575 fnum = OPA->function;
576 if ((fnum & ~0xff000000)==0)
578 PR_RunError(progfuncs, "NULL function from qc (%s).\n", progfuncs->stringtable + pr_xfunction->s_name);
586 static char buffer[1024*1024*8];
587 int size = sizeof buffer;
588 progfuncs->save_ents(progfuncs, buffer, &size, 0);
593 //about to switch. needs caching.
595 //if it's an external call, switch now (before any function pointers are used)
596 PR_MoveParms(progfuncs, (fnum & 0xff000000)>>24, p);
597 PR_SwitchProgs(progfuncs, (fnum & 0xff000000)>>24);
599 newf = &pr_functions[fnum & ~0xff000000];
601 if (newf->first_statement < 0)
602 { // negative statements are built in functions
604 if (pr_typecurrent != 0)
606 PR_MoveParms(progfuncs, 0, pr_typecurrent);
607 PR_SwitchProgs(progfuncs, 0);
609 i = -newf->first_statement;
610 // p = pr_typecurrent;
611 progfuncs->lastcalledbuiltinnumber = i;
612 if (i < externs->numglobalbuiltins)
614 prinst->numtempstringsstack = prinst->numtempstrings;
615 (*externs->globalbuiltins[i]) (progfuncs, (struct globalvars_s *)current_progstate->globals);
616 if (prinst->continuestatement!=-1)
618 st=&pr_statements[prinst->continuestatement];
619 prinst->continuestatement=-1;
625 i -= externs->numglobalbuiltins;
626 if (i >= current_progstate->numbuiltins)
628 // if (newf->first_statement == -0x7fffffff)
629 // ((builtin_t)newf->profile) (progfuncs, (struct globalvars_s *)current_progstate->globals);
631 PR_RunError (progfuncs, "Bad builtin call number - %i", -newf->first_statement);
634 current_progstate->builtins [i] (progfuncs, (struct globalvars_s *)current_progstate->globals);
636 PR_MoveParms(progfuncs, p, pr_typecurrent);
637 // memcpy(&pr_progstate[p].globals[OFS_RETURN], ¤t_progstate->globals[OFS_RETURN], sizeof(vec3_t));
638 PR_SwitchProgs(progfuncs, (progsnum_t)p);
640 //#ifndef DEBUGABLE //decide weather non debugger wants to start debugging.
641 s = st-pr_statements;
646 // PR_MoveParms((OPA->function & 0xff000000)>>24, pr_typecurrent);
647 // PR_SwitchProgs((OPA->function & 0xff000000)>>24);
648 s = PR_EnterFunction (progfuncs, newf, p);
649 st = &pr_statements[s];
659 pr_globals[OFS_RETURN] = pr_globals[st->a];
660 pr_globals[OFS_RETURN+1] = pr_globals[st->a+1];
661 pr_globals[OFS_RETURN+2] = pr_globals[st->a+2];
664 static char buffer[1024*1024*8];
665 int size = sizeof buffer;
666 progfuncs->save_ents(progfuncs, buffer, &size, 0);
669 s = PR_LeaveFunction (progfuncs);
670 st = &pr_statements[s];
671 if (pr_depth == prinst->exitdepth)
679 externs->stateop(progfuncs, OPA->_float, OPB->function);
683 OPC->_int = OPA->_int + OPB->_int;
686 OPC->_float = OPA->_float + (float)OPB->_int;
689 OPC->_float = (float)OPA->_int + OPB->_float;
693 OPC->_int = OPA->_int - OPB->_int;
696 OPC->_float = OPA->_float - (float)OPB->_int;
699 OPC->_float = (float)OPA->_int - OPB->_float;
703 OPC->_float = (float)OPA->_int;
706 OPC->_int = (int)OPA->_float;
710 ptr = (eval_t *)(((qbyte *)sv_edicts) + OPA->_int);
711 OPC->_float = (float)ptr->_int;
715 ptr = (eval_t *)(((qbyte *)sv_edicts) + OPA->_int);
716 OPC->_int = (int)ptr->_float;
720 OPC->_int = (OPA->_int & OPB->_int);
724 OPC->_int = (OPA->_int | OPB->_int);
728 OPC->_int = OPA->_int * OPB->_int;
731 if (OPB->_int == 0) //no division by zero allowed...
734 OPC->_int = OPA->_int / OPB->_int;
737 OPC->_int = (OPA->_int == OPB->_int);
740 OPC->_int = (OPA->_int != OPB->_int);
744 //array/structure reading/writing.
745 case OP_GLOBALADDRESS:
746 OPC->_int = ENGINEPOINTER(&OPA->_int + OPB->_int);
748 case OP_POINTER_ADD: //pointer to 32 bit (remember to *3 for vectors)
749 OPC->_int = OPA->_int + OPB->_int*4;
758 ptr = (eval_t *)(&OPA->_int + OPB->_int);
759 OPC->_int = ptr->_int;
763 ptr = (eval_t *)(&OPA->_int + OPB->_int);
764 OPC->_vector[0] = ptr->_vector[0];
765 OPC->_vector[1] = ptr->_vector[1];
766 OPC->_vector[2] = ptr->_vector[2];
771 case OP_ADD_SF: //(char*)c = (char*)a + (float)b
772 OPC->_int = OPA->_int + (int)OPB->_float;
774 case OP_SUB_S: //(float)c = (char*)a - (char*)b
775 OPC->_int = OPA->_int - OPB->_int;
777 case OP_LOADP_C: //load character from a string
778 ptr = QCPOINTERM(OPA->_int + (int)OPB->_float);
779 OPC->_float = *(unsigned char *)ptr;
787 ptr = QCPOINTERM(OPA->_int + OPB->_int);
788 OPC->_int = ptr->_int;
792 ptr = QCPOINTERM(OPA->_int + OPB->_int);
793 OPC->_vector[0] = ptr->_vector[0];
794 OPC->_vector[1] = ptr->_vector[1];
795 OPC->_vector[2] = ptr->_vector[2];
799 OPC->_int = OPA->_int ^ OPB->_int;
802 OPC->_int = OPA->_int >> OPB->_int;
805 OPC->_int = OPA->_int << OPB->_int;
812 case OP_FETCH_GBL_FNC:
813 i = (int)OPB->_float;
814 if(i < 0 || i > ((eval_t *)&glob[st->a-1])->_int)
816 PR_RunError(progfuncs, "array index out of bounds: %s[%d]", PR_GlobalStringNoContents(progfuncs, st->a), i);
818 t = (eval_t *)&pr_globals[(uofs)st->a + i];
822 i = (int)OPB->_float;
823 if(i < 0 || i > ((eval_t *)&glob[st->a-1])->_int)
825 PR_RunError(progfuncs, "array index out of bounds: %s[%d]", PR_GlobalStringNoContents(progfuncs, st->a), i);
827 t = (eval_t *)&pr_globals[(uofs)st->a + i*3];
828 OPC->_vector[0] = t->_vector[0];
829 OPC->_vector[1] = t->_vector[1];
830 OPC->_vector[2] = t->_vector[2];
834 externs->cstateop(progfuncs, OPA->_float, OPB->_float, fnum);
838 externs->cwstateop(progfuncs, OPA->_float, OPB->_float, fnum);
842 externs->thinktimeop(progfuncs, (struct edict_s *)PROG_TO_EDICT(progfuncs, OPA->edict), OPB->_float);
846 case OP_BITSET: // b (+) a
847 OPB->_float = (float)((int)OPB->_float | (int)OPA->_float);
849 case OP_BITSETP: // .b (+) a
850 ptr = QCPOINTER(OPB);
851 ptr->_float = (float)((int)ptr->_float | (int)OPA->_float);
853 case OP_BITCLR: // b (-) a
854 OPB->_float = (float)((int)OPB->_float & ~((int)OPA->_float));
856 case OP_BITCLRP: // .b (-) a
857 ptr = QCPOINTER(OPB);
858 ptr->_float = (float)((int)ptr->_float & ~((int)OPA->_float));
862 G_FLOAT(OFS_RETURN) = (rand()&0x7fff)/((float)0x7fff);
865 G_FLOAT(OFS_RETURN) = (rand()&0x7fff)/((float)0x7fff)*OPA->_float;
868 if(OPA->_float < OPB->_float)
870 G_FLOAT(OFS_RETURN) = OPA->_float+((rand()&0x7fff)/((float)0x7fff)
871 *(OPB->_float-OPA->_float));
875 G_FLOAT(OFS_RETURN) = OPB->_float+((rand()&0x7fff)/((float)0x7fff)
876 *(OPA->_float-OPB->_float));
880 G_FLOAT(OFS_RETURN+0) = (rand()&0x7fff)/((float)0x7fff);
881 G_FLOAT(OFS_RETURN+1) = (rand()&0x7fff)/((float)0x7fff);
882 G_FLOAT(OFS_RETURN+2) = (rand()&0x7fff)/((float)0x7fff);
885 G_FLOAT(OFS_RETURN+0) = (rand()&0x7fff)/((float)0x7fff)*OPA->_vector[0];
886 G_FLOAT(OFS_RETURN+1) = (rand()&0x7fff)/((float)0x7fff)*OPA->_vector[1];
887 G_FLOAT(OFS_RETURN+2) = (rand()&0x7fff)/((float)0x7fff)*OPA->_vector[2];
890 for(i = 0; i < 3; i++)
892 if(OPA->_vector[i] < OPB->_vector[i])
894 G_FLOAT(OFS_RETURN+i) = OPA->_vector[i]+((rand()&0x7fff)/((float)0x7fff)
895 *(OPB->_vector[i]-OPA->_vector[i]));
899 G_FLOAT(OFS_RETURN+i) = OPB->_vector[i]+(rand()*(1.0f/RAND_MAX)
900 *(OPA->_vector[i]-OPB->_vector[i]));
914 st += (sofs)st->b - 1; // offset the st++
920 if (swtch->_float == OPA->_float)
923 st += (sofs)st->b-1; // -1 to offset the s++
928 if (swtch->_int == OPA->_int)
931 st += (sofs)st->b-1; // -1 to offset the s++
935 if (swtch->_int == OPA->_int)
938 st += (sofs)st->b-1; // -1 to offset the s++
940 if ((!swtch->_int && PR_StringToNative(progfuncs, OPA->string)) || (!OPA->_int && PR_StringToNative(progfuncs, swtch->string))) //one is null (cannot be not both).
942 if (!strcmp(PR_StringToNative(progfuncs, swtch->string), PR_StringToNative(progfuncs, OPA->string)))
945 st += (sofs)st->b-1; // -1 to offset the s++
949 if (swtch->_vector[0] == OPA->_vector[0] && swtch->_vector[1] == OPA->_vector[1] && swtch->_vector[2] == OPA->_vector[2])
952 st += (sofs)st->b-1; // -1 to offset the s++
956 PR_RunError (progfuncs, "OP_CASE with bad/missing OP_SWITCH %i", swtchtype);
964 if (swtch->_float >= OPA->_float && swtch->_float <= OPB->_float)
967 st += (sofs)st->c-1; // -1 to offset the s++
971 PR_RunError (progfuncs, "OP_CASERANGE with bad/missing OP_SWITCH %i", swtchtype);
984 OPC->_int = (OPA->_int & (int)OPB->_float);
987 OPC->_int = (OPA->_int | (int)OPB->_float);
990 OPC->_int = ((int)OPA->_float & OPB->_int);
993 OPC->_int = ((int)OPA->_float | OPB->_int);
997 OPC->_float = (OPA->_int * OPB->_float);
1000 OPC->_float = (OPA->_float * OPB->_int);
1004 OPC->_vector[0] = OPA->_vector[0] * OPB->_int;
1005 OPC->_vector[1] = OPA->_vector[0] * OPB->_int;
1006 OPC->_vector[2] = OPA->_vector[0] * OPB->_int;
1009 OPC->_vector[0] = OPB->_int * OPA->_vector[0];
1010 OPC->_vector[1] = OPB->_int * OPA->_vector[1];
1011 OPC->_vector[2] = OPB->_int * OPA->_vector[2];
1015 OPC->_float = (OPA->_int / OPB->_float);
1018 OPC->_float = (OPA->_float / OPB->_int);
1022 OPC->_int = (OPA->_int && OPB->_int);
1025 OPC->_int = (OPA->_int || OPB->_int);
1029 OPC->_int = (OPA->_int && OPB->_float);
1032 OPC->_int = (OPA->_int || OPB->_float);
1036 OPC->_int = (OPA->_float && OPB->_int);
1039 OPC->_int = (OPA->_float || OPB->_int);
1043 OPC->_int = !OPA->_int;
1047 OPC->_int = (OPA->_int != OPB->_float);
1050 OPC->_int = (OPA->_float != OPB->_int);
1055 case OP_GSTOREP_ENT:
1056 case OP_GSTOREP_FLD: // integers
1058 case OP_GSTOREP_FNC: // pointers
1067 pr_xstatement = st-pr_statements;
1068 PR_RunError(progfuncs, "Extra opcode not implemented\n");
1072 if ((unsigned int)OPA->_int < (unsigned int)st->c || (unsigned int)OPA->_int >= (unsigned int)st->b)
1074 pr_xstatement = st-pr_statements;
1075 PR_RunError(progfuncs, "Progs boundcheck failed. Value is %i.", OPA->_int);
1079 OPC->_int = ENGINEPOINTER(&localstack[localstack_used+pr_spushed]);
1080 pr_spushed += OPA->_int;
1081 if (pr_spushed + localstack_used >= LOCALSTACK_SIZE)
1084 pr_xstatement = st-pr_statements;
1085 PR_RunError(progfuncs, "Progs pushed too much");
1089 pr_spushed -= OPA->_int;
1093 pr_xstatement = st-pr_statements;
1094 PR_RunError(progfuncs, "Progs poped more than it pushed");
1099 if (st->op & 0x8000) //break point!
1101 pr_xstatement = s = st-pr_statements;
1103 printf("Break point hit in %s.\n", pr_xfunction->s_name+progfuncs->stringtable);
1105 pr_trace=1; //this is what it's for
1107 s = ShowStep(progfuncs, s);
1108 st = &pr_statements[s]; //let the user move execution
1109 pr_xstatement = s = st-pr_statements;
1111 goto reeval; //reexecute
1113 pr_xstatement = st-pr_statements;
1114 PR_RunError (progfuncs, "Bad opcode %i", st->op);
1122 #undef pr_statements
1128 #undef ENGINEPOINTER