1 /*
2 Copyright (C) 1996-1997 Id Software, Inc.
3
4 This program is free software; you can redistribute it and/or
5 modify it under the terms of the GNU General Public License
6 as published by the Free Software Foundation; either version 2
7 of the License, or (at your option) any later version.
8
9 This program is distributed in the hope that it will be useful,
10 but WITHOUT ANY WARRANTY; without even the implied warranty of
11 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
12
13 See the GNU General Public License for more details.
14
15 You should have received a copy of the GNU General Public License
16 along with this program; if not, write to the Free Software
17 Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
18
19 */
20 // sv_edict.c -- entity dictionary
21
22 #include "quakedef.h"
23
24 dprograms_t *progs;
25 dfunction_t *pr_functions;
26 char *pr_strings;
27 ddef_t *pr_fielddefs;
28 ddef_t *pr_globaldefs;
29 dstatement_t *pr_statements;
30 globalvars_t *pr_global_struct;
31 float *pr_globals; // same as pr_global_struct
32 int pr_edict_size; // in bytes
33
34 unsigned short pr_crc;
35
36 int type_size[8] = {1,sizeof(string_t)/4,1,3,1,1,sizeof(func_t)/4,sizeof(void *)/4};
37
38 ddef_t *ED_FieldAtOfs (int ofs);
39 qboolean ED_ParseEpair (void *base, ddef_t *key, char *s);
40
41 cvar_t nomonsters = CVAR2("nomonsters", "0");
42 cvar_t gamecfg = CVAR2("gamecfg", "0");
43 cvar_t scratch1 = CVAR2("scratch1", "0");
44 cvar_t scratch2 = CVAR2("scratch2", "0");
45 cvar_t scratch3 = CVAR2("scratch3", "0");
46 cvar_t scratch4 = CVAR2("scratch4", "0");
47 cvar_t savedgamecfg = CVAR3("savedgamecfg", "0", true);
48 cvar_t saved1 = CVAR3("saved1", "0", true);
49 cvar_t saved2 = CVAR3("saved2", "0", true);
50 cvar_t saved3 = CVAR3("saved3", "0", true);
51 cvar_t saved4 = CVAR3("saved4", "0", true);
52
53 #define MAX_FIELD_LEN 64
54 #define GEFV_CACHESIZE 2
55
56 typedef struct {
57 ddef_t *pcache;
58 char field[MAX_FIELD_LEN];
59 } gefv_cache;
60
61 static gefv_cache gefvCache[GEFV_CACHESIZE] = {{NULL, ""}, {NULL, ""}};
62
63 /*
64 =================
65 ED_ClearEdict
66
67 Sets everything to NULL
68 =================
69 */
ED_ClearEdict(edict_t * e)70 void ED_ClearEdict (edict_t *e)
71 {
72 memset (&e->u.v, 0, progs->entityfields * 4);
73 e->free = false;
74 }
75
76 /*
77 =================
78 ED_Alloc
79
80 Either finds a free edict, or allocates a new one.
81 Try to avoid reusing an entity that was recently freed, because it
82 can cause the client to think the entity morphed into something else
83 instead of being removed and recreated, which can cause interpolated
84 angles and bad trails.
85 =================
86 */
ED_Alloc(void)87 edict_t *ED_Alloc (void)
88 {
89 int i;
90 edict_t *e;
91
92 for ( i=svs.maxclients+1 ; i<sv.num_edicts ; i++)
93 {
94 e = EDICT_NUM(i);
95 // the first couple seconds of server time can involve a lot of
96 // freeing and allocating, so relax the replacement policy
97 if (e->free && ( e->freetime < 2 || sv.time - e->freetime > 0.5 ) )
98 {
99 ED_ClearEdict (e);
100 return e;
101 }
102 }
103
104 if (i == MAX_EDICTS)
105 Sys_Error ("ED_Alloc: no free edicts");
106
107 sv.num_edicts++;
108 e = EDICT_NUM(i);
109 ED_ClearEdict (e);
110
111 return e;
112 }
113
114 /*
115 =================
116 ED_Free
117
118 Marks the edict as free
119 FIXME: walk all entities and NULL out references to this entity
120 =================
121 */
ED_Free(edict_t * ed)122 void ED_Free (edict_t *ed)
123 {
124 SV_UnlinkEdict (ed); // unlink from world bsp
125
126 ed->free = true;
127 ed->u.v.model = 0;
128 ed->u.v.takedamage = 0;
129 ed->u.v.modelindex = 0;
130 ed->u.v.colormap = 0;
131 ed->u.v.skin = 0;
132 ed->u.v.frame = 0;
133 VectorCopy (vec3_origin, ed->u.v.origin);
134 VectorCopy (vec3_origin, ed->u.v.angles);
135 ed->u.v.nextthink = -1;
136 ed->u.v.solid = 0;
137
138 ed->freetime = sv.time;
139 }
140
141 //===========================================================================
142
143 /*
144 ============
145 ED_GlobalAtOfs
146 ============
147 */
ED_GlobalAtOfs(int ofs)148 ddef_t *ED_GlobalAtOfs (int ofs)
149 {
150 ddef_t *def;
151 int i;
152
153 for (i=0 ; i<progs->numglobaldefs ; i++)
154 {
155 def = &pr_globaldefs[i];
156 if (def->ofs == ofs)
157 return def;
158 }
159 return NULL;
160 }
161
162 /*
163 ============
164 ED_FieldAtOfs
165 ============
166 */
ED_FieldAtOfs(int ofs)167 ddef_t *ED_FieldAtOfs (int ofs)
168 {
169 ddef_t *def;
170 int i;
171
172 for (i=0 ; i<progs->numfielddefs ; i++)
173 {
174 def = &pr_fielddefs[i];
175 if (def->ofs == ofs)
176 return def;
177 }
178 return NULL;
179 }
180
181 /*
182 ============
183 ED_FindField
184 ============
185 */
ED_FindField(const char * name)186 ddef_t *ED_FindField (const char *name)
187 {
188 ddef_t *def;
189 int i;
190
191 for (i=0 ; i<progs->numfielddefs ; i++)
192 {
193 def = &pr_fielddefs[i];
194 if (!strcmp(pr_strings + def->s_name,name) )
195 return def;
196 }
197 return NULL;
198 }
199
200
201 /*
202 ============
203 ED_FindGlobal
204 ============
205 */
ED_FindGlobal(const char * name)206 ddef_t *ED_FindGlobal (const char *name)
207 {
208 ddef_t *def;
209 int i;
210
211 for (i=0 ; i<progs->numglobaldefs ; i++)
212 {
213 def = &pr_globaldefs[i];
214 if (!strcmp(pr_strings + def->s_name,name) )
215 return def;
216 }
217 return NULL;
218 }
219
220
221 /*
222 ============
223 ED_FindFunction
224 ============
225 */
ED_FindFunction(const char * name)226 dfunction_t *ED_FindFunction (const char *name)
227 {
228 dfunction_t *func;
229 int i;
230
231 for (i=0 ; i<progs->numfunctions ; i++)
232 {
233 func = &pr_functions[i];
234 if (!strcmp(pr_strings + func->s_name,name) )
235 return func;
236 }
237 return NULL;
238 }
239
240
GetEdictFieldValue(edict_t * ed,const char * field)241 eval_t *GetEdictFieldValue(edict_t *ed, const char *field)
242 {
243 ddef_t *def = NULL;
244 int i;
245 static int rep = 0;
246
247 for (i=0 ; i<GEFV_CACHESIZE ; i++)
248 {
249 if (!strcmp(field, gefvCache[i].field))
250 {
251 def = gefvCache[i].pcache;
252 goto Done;
253 }
254 }
255
256 def = ED_FindField (field);
257
258 if (strlen(field) < MAX_FIELD_LEN)
259 {
260 gefvCache[rep].pcache = def;
261 strcpy (gefvCache[rep].field, field);
262 rep ^= 1;
263 }
264
265 Done:
266 if (!def)
267 return NULL;
268
269 return (eval_t *)((char *)&ed->u.v + def->ofs*4);
270 }
271
272
273 /*
274 ============
275 PR_ValueString
276
277 Returns a string describing *data in a type specific manner
278 =============
279 */
PR_ValueString(etype_t type,eval_t * val)280 char *PR_ValueString (etype_t type, eval_t *val)
281 {
282 static char line[256];
283 ddef_t *def;
284 dfunction_t *f;
285
286 type = (etype_t) (type & ~DEF_SAVEGLOBAL);
287
288 switch (type)
289 {
290 case ev_string:
291 sprintf (line, "%s", pr_strings + val->string);
292 break;
293 case ev_entity:
294 sprintf (line, "entity %i", NUM_FOR_EDICT(PROG_TO_EDICT(val->edict)) );
295 break;
296 case ev_function:
297 f = pr_functions + val->function;
298 sprintf (line, "%s()", pr_strings + f->s_name);
299 break;
300 case ev_field:
301 def = ED_FieldAtOfs ( val->_int );
302 sprintf (line, ".%s", pr_strings + def->s_name);
303 break;
304 case ev_void:
305 sprintf (line, "void");
306 break;
307 case ev_float:
308 sprintf (line, "%5.1f", val->_float);
309 break;
310 case ev_vector:
311 sprintf (line, "'%5.1f %5.1f %5.1f'", val->vector[0], val->vector[1], val->vector[2]);
312 break;
313 case ev_pointer:
314 sprintf (line, "pointer");
315 break;
316 default:
317 sprintf (line, "bad type %i", type);
318 break;
319 }
320
321 return line;
322 }
323
324 /*
325 ============
326 PR_UglyValueString
327
328 Returns a string describing *data in a type specific manner
329 Easier to parse than PR_ValueString
330 =============
331 */
PR_UglyValueString(etype_t type,eval_t * val)332 char *PR_UglyValueString (etype_t type, eval_t *val)
333 {
334 static char line[256];
335 ddef_t *def;
336 dfunction_t *f;
337
338 type = (etype_t) (type & ~DEF_SAVEGLOBAL);
339
340 switch (type)
341 {
342 case ev_string:
343 sprintf (line, "%s", pr_strings + val->string);
344 break;
345 case ev_entity:
346 sprintf (line, "%i", NUM_FOR_EDICT(PROG_TO_EDICT(val->edict)));
347 break;
348 case ev_function:
349 f = pr_functions + val->function;
350 sprintf (line, "%s", pr_strings + f->s_name);
351 break;
352 case ev_field:
353 def = ED_FieldAtOfs ( val->_int );
354 sprintf (line, "%s", pr_strings + def->s_name);
355 break;
356 case ev_void:
357 sprintf (line, "void");
358 break;
359 case ev_float:
360 sprintf (line, "%f", val->_float);
361 break;
362 case ev_vector:
363 sprintf (line, "%f %f %f", val->vector[0], val->vector[1], val->vector[2]);
364 break;
365 default:
366 sprintf (line, "bad type %i", type);
367 break;
368 }
369
370 return line;
371 }
372
373 /*
374 ============
375 PR_GlobalString
376
377 Returns a string with a description and the contents of a global,
378 padded to 20 field width
379 ============
380 */
PR_GlobalString(int ofs)381 char *PR_GlobalString (int ofs)
382 {
383 char *s;
384 int i;
385 ddef_t *def;
386 void *val;
387 static char line[128];
388
389 val = (void *)&pr_globals[ofs];
390 def = ED_GlobalAtOfs(ofs);
391 if (!def)
392 sprintf (line,"%i(??""?)", ofs);
393 else
394 {
395 s = PR_ValueString ((etype_t) def->type, (eval_t*) val);
396 sprintf (line,"%i(%s)%s", ofs, pr_strings + def->s_name, s);
397 }
398
399 i = strlen(line);
400 for ( ; i<20 ; i++)
401 strcat (line," ");
402 strcat (line," ");
403
404 return line;
405 }
406
PR_GlobalStringNoContents(int ofs)407 char *PR_GlobalStringNoContents (int ofs)
408 {
409 int i;
410 ddef_t *def;
411 static char line[128];
412
413 def = ED_GlobalAtOfs(ofs);
414 if (!def)
415 sprintf (line,"%i(??""?)", ofs);
416 else
417 sprintf (line,"%i(%s)", ofs, pr_strings + def->s_name);
418
419 i = strlen(line);
420 for ( ; i<20 ; i++)
421 strcat (line," ");
422 strcat (line," ");
423
424 return line;
425 }
426
427
428 /*
429 =============
430 ED_Print
431
432 For debugging
433 =============
434 */
ED_Print(edict_t * ed)435 void ED_Print (edict_t *ed)
436 {
437 int l;
438 ddef_t *d;
439 int *v;
440 int i, j;
441 char *name;
442 int type;
443
444 if (ed->free)
445 {
446 Con_Printf ("FREE\n");
447 return;
448 }
449
450 Con_Printf("\nEDICT %i:\n", NUM_FOR_EDICT(ed));
451 for (i=1 ; i<progs->numfielddefs ; i++)
452 {
453 d = &pr_fielddefs[i];
454 name = pr_strings + d->s_name;
455 if (name[strlen(name)-2] == '_')
456 continue; // skip _x, _y, _z vars
457
458 v = (int *)((char *)&ed->u.v + d->ofs*4);
459
460 // if the value is still all 0, skip the field
461 type = d->type & ~DEF_SAVEGLOBAL;
462
463 for (j=0 ; j<type_size[type] ; j++)
464 if (v[j])
465 break;
466 if (j == type_size[type])
467 continue;
468
469 Con_Printf ("%s",name);
470 l = strlen (name);
471 while (l++ < 15)
472 Con_Printf (" ");
473
474 Con_Printf ("%s\n", PR_ValueString((etype_t) d->type, (eval_t *)v));
475 }
476 }
477
478 /*
479 =============
480 ED_Write
481
482 For savegames
483 =============
484 */
ED_Write(FILE * f,edict_t * ed)485 void ED_Write (FILE *f, edict_t *ed)
486 {
487 ddef_t *d;
488 int *v;
489 int i, j;
490 char *name;
491 int type;
492
493 fprintf (f, "{\n");
494
495 if (ed->free)
496 {
497 fprintf (f, "}\n");
498 return;
499 }
500
501 for (i=1 ; i<progs->numfielddefs ; i++)
502 {
503 d = &pr_fielddefs[i];
504 name = pr_strings + d->s_name;
505 if (name[strlen(name)-2] == '_')
506 continue; // skip _x, _y, _z vars
507
508 v = (int *)((char *)&ed->u.v + d->ofs*4);
509
510 // if the value is still all 0, skip the field
511 type = d->type & ~DEF_SAVEGLOBAL;
512 for (j=0 ; j<type_size[type] ; j++)
513 if (v[j])
514 break;
515 if (j == type_size[type])
516 continue;
517
518 fprintf (f,"\"%s\" ",name);
519 fprintf (f,"\"%s\"\n", PR_UglyValueString((etype_t) d->type, (eval_t *)v));
520 }
521
522 fprintf (f, "}\n");
523 }
524
ED_PrintNum(int ent)525 void ED_PrintNum (int ent)
526 {
527 ED_Print (EDICT_NUM(ent));
528 }
529
530 /*
531 =============
532 ED_PrintEdicts
533
534 For debugging, prints all the entities in the current server
535 =============
536 */
ED_PrintEdicts(void)537 void ED_PrintEdicts (void)
538 {
539 int i;
540
541 Con_Printf ("%i entities\n", sv.num_edicts);
542 for (i=0 ; i<sv.num_edicts ; i++)
543 ED_PrintNum (i);
544 }
545
546 /*
547 =============
548 ED_PrintEdict_f
549
550 For debugging, prints a single edicy
551 =============
552 */
ED_PrintEdict_f(void)553 void ED_PrintEdict_f (void)
554 {
555 int i;
556
557 i = Q_atoi (Cmd_Argv(1));
558 if (i >= sv.num_edicts)
559 {
560 Con_Printf("Bad edict number\n");
561 return;
562 }
563 ED_PrintNum (i);
564 }
565
566 /*
567 =============
568 ED_Count
569
570 For debugging
571 =============
572 */
ED_Count(void)573 void ED_Count (void)
574 {
575 int i;
576 edict_t *ent;
577 int active, models, solid, step;
578
579 active = models = solid = step = 0;
580 for (i=0 ; i<sv.num_edicts ; i++)
581 {
582 ent = EDICT_NUM(i);
583 if (ent->free)
584 continue;
585 active++;
586 if (ent->u.v.solid)
587 solid++;
588 if (ent->u.v.model)
589 models++;
590 if (ent->u.v.movetype == MOVETYPE_STEP)
591 step++;
592 }
593
594 Con_Printf ("num_edicts:%3i\n", sv.num_edicts);
595 Con_Printf ("active :%3i\n", active);
596 Con_Printf ("view :%3i\n", models);
597 Con_Printf ("touch :%3i\n", solid);
598 Con_Printf ("step :%3i\n", step);
599
600 }
601
602 /*
603 ==============================================================================
604
605 ARCHIVING GLOBALS
606
607 FIXME: need to tag constants, doesn't really work
608 ==============================================================================
609 */
610
611 /*
612 =============
613 ED_WriteGlobals
614 =============
615 */
ED_WriteGlobals(FILE * f)616 void ED_WriteGlobals (FILE *f)
617 {
618 ddef_t *def;
619 int i;
620 char *name;
621 int type;
622
623 fprintf (f,"{\n");
624 for (i=0 ; i<progs->numglobaldefs ; i++)
625 {
626 def = &pr_globaldefs[i];
627 type = def->type;
628 if ( !(def->type & DEF_SAVEGLOBAL) )
629 continue;
630 type &= ~DEF_SAVEGLOBAL;
631
632 if (type != ev_string
633 && type != ev_float
634 && type != ev_entity)
635 continue;
636
637 name = pr_strings + def->s_name;
638 fprintf (f,"\"%s\" ", name);
639 fprintf (f,"\"%s\"\n", PR_UglyValueString((etype_t) type, (eval_t *)&pr_globals[def->ofs]));
640 }
641 fprintf (f,"}\n");
642 }
643
644 /*
645 =============
646 ED_ParseGlobals
647 =============
648 */
ED_ParseGlobals(char * data)649 void ED_ParseGlobals (char *data)
650 {
651 char keyname[64];
652 ddef_t *key;
653
654 while (1)
655 {
656 // parse key
657 data = COM_Parse (data);
658 if (com_token[0] == '}')
659 break;
660 if (!data)
661 Sys_Error ("ED_ParseEntity: EOF without closing brace");
662
663 strcpy (keyname, com_token);
664
665 // parse value
666 data = COM_Parse (data);
667 if (!data)
668 Sys_Error ("ED_ParseEntity: EOF without closing brace");
669
670 if (com_token[0] == '}')
671 Sys_Error ("ED_ParseEntity: closing brace without data");
672
673 key = ED_FindGlobal (keyname);
674 if (!key)
675 {
676 Con_Printf ("'%s' is not a global\n", keyname);
677 continue;
678 }
679
680 if (!ED_ParseEpair ((void *)pr_globals, key, com_token))
681 Host_Error ("ED_ParseGlobals: parse error");
682 }
683 }
684
685 //============================================================================
686
687
688 /*
689 =============
690 ED_NewString
691 =============
692 */
ED_NewString(char * string)693 char *ED_NewString (char *string)
694 {
695 char *new_, *new_p;
696 int i,l;
697
698 l = strlen(string) + 1;
699 new_ = (char*) Hunk_Alloc (l);
700 new_p = new_;
701
702 for (i=0 ; i< l ; i++)
703 {
704 if (string[i] == '\\' && i < l-1)
705 {
706 i++;
707 if (string[i] == 'n')
708 *new_p++ = '\n';
709 else
710 *new_p++ = '\\';
711 }
712 else
713 *new_p++ = string[i];
714 }
715
716 return new_;
717 }
718
719
720 /*
721 =============
722 ED_ParseEval
723
724 Can parse either fields or globals
725 returns false if error
726 =============
727 */
ED_ParseEpair(void * base,ddef_t * key,char * s)728 qboolean ED_ParseEpair (void *base, ddef_t *key, char *s)
729 {
730 int i;
731 char string[128];
732 ddef_t *def;
733 char *v, *w;
734 void *d;
735 dfunction_t *func;
736
737 d = (void *)((int *)base + key->ofs);
738
739 switch (key->type & ~DEF_SAVEGLOBAL)
740 {
741 case ev_string:
742 *(string_t *)d = ED_NewString (s) - pr_strings;
743 break;
744
745 case ev_float:
746 *(float *)d = atof (s);
747 break;
748
749 case ev_vector:
750 strcpy (string, s);
751 v = string;
752 w = string;
753 for (i=0 ; i<3 ; i++)
754 {
755 while (*v && *v != ' ')
756 v++;
757 *v = 0;
758 ((float *)d)[i] = atof (w);
759 w = v = v+1;
760 }
761 break;
762
763 case ev_entity:
764 *(int *)d = EDICT_TO_PROG(EDICT_NUM(atoi (s)));
765 break;
766
767 case ev_field:
768 def = ED_FindField (s);
769 if (!def)
770 {
771 Con_Printf ("Can't find field %s\n", s);
772 return false;
773 }
774 *(int *)d = G_INT(def->ofs);
775 break;
776
777 case ev_function:
778 func = ED_FindFunction (s);
779 if (!func)
780 {
781 Con_Printf ("Can't find function %s\n", s);
782 return false;
783 }
784 *(func_t *)d = func - pr_functions;
785 break;
786
787 default:
788 break;
789 }
790 return true;
791 }
792
793 /*
794 ====================
795 ED_ParseEdict
796
797 Parses an edict out of the given string, returning the new position
798 ed should be a properly initialized empty edict.
799 Used for initial level load and for savegames.
800 ====================
801 */
ED_ParseEdict(char * data,edict_t * ent)802 char *ED_ParseEdict (char *data, edict_t *ent)
803 {
804 ddef_t *key;
805 qboolean anglehack;
806 qboolean init;
807 char keyname[256];
808 int n;
809
810 init = false;
811
812 // clear it
813 if (ent != sv.edicts) // hack
814 memset (&ent->u.v, 0, progs->entityfields * 4);
815
816 // go through all the dictionary pairs
817 while (1)
818 {
819 // parse key
820 data = COM_Parse (data);
821 if (com_token[0] == '}')
822 break;
823 if (!data)
824 Sys_Error ("ED_ParseEntity: EOF without closing brace");
825
826 // anglehack is to allow QuakeEd to write single scalar angles
827 // and allow them to be turned into vectors. (FIXME...)
828 if (!strcmp(com_token, "angle"))
829 {
830 strcpy (com_token, "angles");
831 anglehack = true;
832 }
833 else
834 anglehack = false;
835
836 // FIXME: change light to _light to get rid of this hack
837 if (!strcmp(com_token, "light"))
838 strcpy (com_token, "light_lev"); // hack for single light def
839
840 strcpy (keyname, com_token);
841
842 // another hack to fix heynames with trailing spaces
843 n = strlen(keyname);
844 while (n && keyname[n-1] == ' ')
845 {
846 keyname[n-1] = 0;
847 n--;
848 }
849
850 // parse value
851 data = COM_Parse (data);
852 if (!data)
853 Sys_Error ("ED_ParseEntity: EOF without closing brace");
854
855 if (com_token[0] == '}')
856 Sys_Error ("ED_ParseEntity: closing brace without data");
857
858 init = true;
859
860 // keynames with a leading underscore are used for utility comments,
861 // and are immediately discarded by quake
862 if (keyname[0] == '_')
863 continue;
864
865 key = ED_FindField (keyname);
866 if (!key)
867 {
868 Con_Printf ("'%s' is not a field\n", keyname);
869 continue;
870 }
871
872 if (anglehack)
873 {
874 char temp[32];
875 strcpy (temp, com_token);
876 sprintf (com_token, "0 %s 0", temp);
877 }
878
879 if (!ED_ParseEpair ((void *)&ent->u.v, key, com_token))
880 Host_Error ("ED_ParseEdict: parse error");
881 }
882
883 if (!init)
884 ent->free = true;
885
886 return data;
887 }
888
889
890 /*
891 ================
892 ED_LoadFromFile
893
894 The entities are directly placed in the array, rather than allocated with
895 ED_Alloc, because otherwise an error loading the map would have entity
896 number references out of order.
897
898 Creates a server's entity / program execution context by
899 parsing textual entity definitions out of an ent file.
900
901 Used for both fresh maps and savegame loads. A fresh map would also need
902 to call ED_CallSpawnFunctions () to let the objects initialize themselves.
903 ================
904 */
ED_LoadFromFile(char * data)905 void ED_LoadFromFile (char *data)
906 {
907 edict_t *ent;
908 int inhibit;
909 dfunction_t *func;
910
911 ent = NULL;
912 inhibit = 0;
913 pr_global_struct->time = sv.time;
914
915 // parse ents
916 while (1)
917 {
918 // parse the opening brace
919 data = COM_Parse (data);
920 if (!data)
921 break;
922 if (com_token[0] != '{')
923 Sys_Error ("ED_LoadFromFile: found %s when expecting {",com_token);
924
925 if (!ent)
926 ent = EDICT_NUM(0);
927 else
928 ent = ED_Alloc ();
929 data = ED_ParseEdict (data, ent);
930
931 // remove things from different skill levels or deathmatch
932 if (deathmatch.value)
933 {
934 if (((int)ent->u.v.spawnflags & SPAWNFLAG_NOT_DEATHMATCH))
935 {
936 ED_Free (ent);
937 inhibit++;
938 continue;
939 }
940 }
941 else if ((current_skill == 0 && ((int)ent->u.v.spawnflags & SPAWNFLAG_NOT_EASY))
942 || (current_skill == 1 && ((int)ent->u.v.spawnflags & SPAWNFLAG_NOT_MEDIUM))
943 || (current_skill >= 2 && ((int)ent->u.v.spawnflags & SPAWNFLAG_NOT_HARD)) )
944 {
945 ED_Free (ent);
946 inhibit++;
947 continue;
948 }
949
950 //
951 // immediately call spawn function
952 //
953 if (!ent->u.v.classname)
954 {
955 Con_Printf ("No classname for:\n");
956 ED_Print (ent);
957 ED_Free (ent);
958 continue;
959 }
960
961 // look for the spawn function
962 func = ED_FindFunction ( pr_strings + ent->u.v.classname );
963
964 if (!func)
965 {
966 Con_Printf ("No spawn function for:\n");
967 ED_Print (ent);
968 ED_Free (ent);
969 continue;
970 }
971
972 pr_global_struct->self = EDICT_TO_PROG(ent);
973 PR_ExecuteProgram (func - pr_functions);
974 }
975
976 Con_DPrintf ("%i entities inhibited\n", inhibit);
977 }
978
979
980 /*
981 ===============
982 PR_LoadProgs
983 ===============
984 */
PR_LoadProgs(void)985 void PR_LoadProgs (void)
986 {
987 int i;
988
989 // flush the non-C variable lookup cache
990 for (i=0 ; i<GEFV_CACHESIZE ; i++)
991 gefvCache[i].field[0] = 0;
992
993 CRC_Init (&pr_crc);
994
995 progs = (dprograms_t *)COM_LoadHunkFile ("progs.dat");
996 if (!progs)
997 Sys_Error ("PR_LoadProgs: couldn't load progs.dat");
998 Con_DPrintf ("Programs occupy %iK.\n", com_filesize/1024);
999
1000 for (i=0 ; i<com_filesize ; i++)
1001 CRC_ProcessByte (&pr_crc, ((byte *)progs)[i]);
1002
1003 // byte swap the header
1004 for (i=0 ; i< (int) (sizeof(*progs)/4) ; i++)
1005 ((int *)progs)[i] = LittleLong ( ((int *)progs)[i] );
1006
1007 if (progs->version != PROG_VERSION)
1008 Sys_Error ("progs.dat has wrong version number (%i should be %i)", progs->version, PROG_VERSION);
1009 if (progs->crc != PROGHEADER_CRC)
1010 Sys_Error ("progs.dat system vars have been modified, progdefs.h is out of date");
1011
1012 pr_functions = (dfunction_t *)((byte *)progs + progs->ofs_functions);
1013 pr_strings = (char *)progs + progs->ofs_strings;
1014 pr_globaldefs = (ddef_t *)((byte *)progs + progs->ofs_globaldefs);
1015 pr_fielddefs = (ddef_t *)((byte *)progs + progs->ofs_fielddefs);
1016 pr_statements = (dstatement_t *)((byte *)progs + progs->ofs_statements);
1017
1018 pr_global_struct = (globalvars_t *)((byte *)progs + progs->ofs_globals);
1019 pr_globals = (float *)pr_global_struct;
1020
1021 pr_edict_size = progs->entityfields * 4 + sizeof (edict_t) - sizeof(entvars_t);
1022
1023 // byte swap the lumps
1024 for (i=0 ; i<progs->numstatements ; i++)
1025 {
1026 pr_statements[i].op = LittleShort(pr_statements[i].op);
1027 pr_statements[i].a = LittleShort(pr_statements[i].a);
1028 pr_statements[i].b = LittleShort(pr_statements[i].b);
1029 pr_statements[i].c = LittleShort(pr_statements[i].c);
1030 }
1031
1032 for (i=0 ; i<progs->numfunctions; i++)
1033 {
1034 pr_functions[i].first_statement = LittleLong (pr_functions[i].first_statement);
1035 pr_functions[i].parm_start = LittleLong (pr_functions[i].parm_start);
1036 pr_functions[i].s_name = LittleLong (pr_functions[i].s_name);
1037 pr_functions[i].s_file = LittleLong (pr_functions[i].s_file);
1038 pr_functions[i].numparms = LittleLong (pr_functions[i].numparms);
1039 pr_functions[i].locals = LittleLong (pr_functions[i].locals);
1040 }
1041
1042 for (i=0 ; i<progs->numglobaldefs ; i++)
1043 {
1044 pr_globaldefs[i].type = LittleShort (pr_globaldefs[i].type);
1045 pr_globaldefs[i].ofs = LittleShort (pr_globaldefs[i].ofs);
1046 pr_globaldefs[i].s_name = LittleLong (pr_globaldefs[i].s_name);
1047 }
1048
1049 for (i=0 ; i<progs->numfielddefs ; i++)
1050 {
1051 pr_fielddefs[i].type = LittleShort (pr_fielddefs[i].type);
1052 if (pr_fielddefs[i].type & DEF_SAVEGLOBAL)
1053 Sys_Error ("PR_LoadProgs: pr_fielddefs[i].type & DEF_SAVEGLOBAL");
1054 pr_fielddefs[i].ofs = LittleShort (pr_fielddefs[i].ofs);
1055 pr_fielddefs[i].s_name = LittleLong (pr_fielddefs[i].s_name);
1056 }
1057
1058 for (i=0 ; i<progs->numglobals ; i++)
1059 ((int *)pr_globals)[i] = LittleLong (((int *)pr_globals)[i]);
1060 }
1061
1062
1063 /*
1064 ===============
1065 PR_Init
1066 ===============
1067 */
PR_Init(void)1068 void PR_Init (void)
1069 {
1070 Cmd_AddCommand ("edict", ED_PrintEdict_f);
1071 Cmd_AddCommand ("edicts", ED_PrintEdicts);
1072 Cmd_AddCommand ("edictcount", ED_Count);
1073 Cmd_AddCommand ("profile", PR_Profile_f);
1074 Cvar_RegisterVariable (&nomonsters);
1075 Cvar_RegisterVariable (&gamecfg);
1076 Cvar_RegisterVariable (&scratch1);
1077 Cvar_RegisterVariable (&scratch2);
1078 Cvar_RegisterVariable (&scratch3);
1079 Cvar_RegisterVariable (&scratch4);
1080 Cvar_RegisterVariable (&savedgamecfg);
1081 Cvar_RegisterVariable (&saved1);
1082 Cvar_RegisterVariable (&saved2);
1083 Cvar_RegisterVariable (&saved3);
1084 Cvar_RegisterVariable (&saved4);
1085 }
1086
1087
1088
EDICT_NUM(int n)1089 edict_t *EDICT_NUM(int n)
1090 {
1091 if (n < 0 || n >= sv.max_edicts)
1092 Sys_Error ("EDICT_NUM: bad number %i", n);
1093 return (edict_t *)((byte *)sv.edicts+ (n)*pr_edict_size);
1094 }
1095
NUM_FOR_EDICT(edict_t * e)1096 int NUM_FOR_EDICT(edict_t *e)
1097 {
1098 int b;
1099
1100 b = (byte *)e - (byte *)sv.edicts;
1101 b = b / pr_edict_size;
1102
1103 if (b < 0 || b >= sv.num_edicts)
1104 Sys_Error ("NUM_FOR_EDICT: bad pointer");
1105 return b;
1106 }
1107