DarkPlaces
Game engine based on the Quake 1 engine by id Software, developed by LadyHavoc
 
sv_ents5.c
Go to the documentation of this file.
1#include "quakedef.h"
2#include "protocol.h"
3
4static double anim_reducetime(double t, double frameduration, double maxtime)
5{
6 if(t < 0) // clamp to non-negative
7 return 0;
8 if(t <= maxtime) // time can be represented normally
9 return t;
10 if(frameduration == 0) // don't like dividing by zero
11 return t;
12 if(maxtime <= 2 * frameduration) // if two frames don't fit, we better not do this
13 return t;
14 t -= frameduration * ceil((t - maxtime) / frameduration);
15 // now maxtime - frameduration < t <= maxtime
16 return t;
17}
18
19// see VM_SV_frameduration
20static double anim_frameduration(model_t *model, int framenum)
21{
22 if (!model || !model->animscenes || framenum < 0 || framenum >= model->numframes)
23 return 0;
24 if(model->animscenes[framenum].framerate)
25 return model->animscenes[framenum].framecount / model->animscenes[framenum].framerate;
26 return 0;
27}
28
30{
31 // all the [maxedicts] memory is allocated at once, so there's only one
32 // thing to free
33 if (d->maxedicts)
35 Mem_Free(d);
36}
37
39{
40 if (d->maxedicts < newmax)
41 {
42 unsigned char *data;
43 int oldmaxedicts = d->maxedicts;
44 int *olddeltabits = d->deltabits;
45 unsigned char *oldpriorities = d->priorities;
46 int *oldupdateframenum = d->updateframenum;
47 entity_state_t *oldstates = d->states;
48 unsigned char *oldvisiblebits = d->visiblebits;
49 d->maxedicts = newmax;
50 data = (unsigned char *)Mem_Alloc(sv_mempool, d->maxedicts * sizeof(int) + d->maxedicts * sizeof(unsigned char) + d->maxedicts * sizeof(int) + d->maxedicts * sizeof(entity_state_t) + (d->maxedicts+7)/8 * sizeof(unsigned char));
51 d->deltabits = (int *)data;data += d->maxedicts * sizeof(int);
52 d->priorities = (unsigned char *)data;data += d->maxedicts * sizeof(unsigned char);
53 d->updateframenum = (int *)data;data += d->maxedicts * sizeof(int);
54 d->states = (entity_state_t *)data;data += d->maxedicts * sizeof(entity_state_t);
55 d->visiblebits = (unsigned char *)data;data += (d->maxedicts+7)/8 * sizeof(unsigned char);
56 if (oldmaxedicts)
57 {
58 memcpy(d->deltabits, olddeltabits, oldmaxedicts * sizeof(int));
59 memcpy(d->priorities, oldpriorities, oldmaxedicts * sizeof(unsigned char));
60 memcpy(d->updateframenum, oldupdateframenum, oldmaxedicts * sizeof(int));
61 memcpy(d->states, oldstates, oldmaxedicts * sizeof(entity_state_t));
62 memcpy(d->visiblebits, oldvisiblebits, (oldmaxedicts+7)/8 * sizeof(unsigned char));
63 // the previous buffers were a single allocation, so just one free
64 Mem_Free(olddeltabits);
65 }
66 }
67}
68
69static int EntityState5_Priority(entityframe5_database_t *d, int stateindex)
70{
71 int limit, priority;
72 entity_state_t *s = NULL; // hush compiler warning by initializing this
73 // if it is the player, update urgently
74 if (stateindex == d->viewentnum)
76 // priority increases each frame no matter what happens
77 priority = d->priorities[stateindex] + 1;
78 // players get an extra priority boost
79 if (stateindex <= svs.maxclients)
80 priority++;
81 // remove dead entities very quickly because they are just 2 bytes
82 if (d->states[stateindex].active != ACTIVE_NETWORK)
83 {
84 priority++;
85 return bound(1, priority, ENTITYFRAME5_PRIORITYLEVELS - 1);
86 }
87 // certain changes are more noticable than others
89 priority++;
90 // find the root entity this one is attached to, and judge relevance by it
91 for (limit = 0;limit < 256;limit++)
92 {
93 s = d->states + stateindex;
94 if (s->flags & RENDER_VIEWMODEL)
95 stateindex = d->viewentnum;
96 else if (s->tagentity)
97 stateindex = s->tagentity;
98 else
99 break;
100 if (d->maxedicts < stateindex)
101 EntityFrame5_ExpandEdicts(d, (stateindex+256)&~255);
102 }
103 if (limit >= 256)
104 Con_DPrintf("Protocol: Runaway loop recursing tagentity links on entity %i\n", stateindex);
105 // now that we have the parent entity we can make some decisions based on
106 // distance from the player
107 if (VectorDistance(d->states[d->viewentnum].netcenter, s->netcenter) < 1024.0f)
108 priority++;
109 return bound(1, priority, ENTITYFRAME5_PRIORITYLEVELS - 1);
110}
111
113{
114 unsigned int bits = 0;
115 if (n->active == ACTIVE_NETWORK)
116 {
117 if (o->active != ACTIVE_NETWORK)
118 bits |= E5_FULLUPDATE;
119 if (!VectorCompare(o->origin, n->origin))
120 bits |= E5_ORIGIN;
121 if (!VectorCompare(o->angles, n->angles))
122 bits |= E5_ANGLES;
123 if (o->modelindex != n->modelindex)
124 bits |= E5_MODEL;
125 if (o->frame != n->frame)
126 bits |= E5_FRAME;
127 if (o->skin != n->skin)
128 bits |= E5_SKIN;
129 if (o->effects != n->effects)
130 bits |= E5_EFFECTS;
131 if (o->flags != n->flags)
132 bits |= E5_FLAGS;
133 if (o->alpha != n->alpha)
134 bits |= E5_ALPHA;
135 if (o->scale != n->scale)
136 bits |= E5_SCALE;
137 if (o->colormap != n->colormap)
138 bits |= E5_COLORMAP;
139 if (o->tagentity != n->tagentity || o->tagindex != n->tagindex)
140 bits |= E5_ATTACHMENT;
141 if (o->light[0] != n->light[0] || o->light[1] != n->light[1] || o->light[2] != n->light[2] || o->light[3] != n->light[3] || o->lightstyle != n->lightstyle || o->lightpflags != n->lightpflags)
142 bits |= E5_LIGHT;
143 if (o->glowsize != n->glowsize || o->glowcolor != n->glowcolor)
144 bits |= E5_GLOW;
145 if (o->colormod[0] != n->colormod[0] || o->colormod[1] != n->colormod[1] || o->colormod[2] != n->colormod[2])
146 bits |= E5_COLORMOD;
147 if (o->glowmod[0] != n->glowmod[0] || o->glowmod[1] != n->glowmod[1] || o->glowmod[2] != n->glowmod[2])
148 bits |= E5_GLOWMOD;
149 if (n->flags & RENDER_COMPLEXANIMATION)
150 {
151 if ((o->skeletonobject.model && o->skeletonobject.relativetransforms) != (n->skeletonobject.model && n->skeletonobject.relativetransforms))
152 {
153 bits |= E5_COMPLEXANIMATION;
154 }
156 {
157 if(o->modelindex != n->modelindex)
158 bits |= E5_COMPLEXANIMATION;
159 else if(o->skeletonobject.model->num_bones != n->skeletonobject.model->num_bones)
160 bits |= E5_COMPLEXANIMATION;
161 else if(memcmp(o->skeletonobject.relativetransforms, n->skeletonobject.relativetransforms, o->skeletonobject.model->num_bones * sizeof(*o->skeletonobject.relativetransforms)))
162 bits |= E5_COMPLEXANIMATION;
163 }
164 else if (memcmp(o->framegroupblend, n->framegroupblend, sizeof(o->framegroupblend)))
165 {
166 bits |= E5_COMPLEXANIMATION;
167 }
168 }
169 if (o->traileffectnum != n->traileffectnum)
170 bits |= E5_TRAILEFFECTNUM;
171 }
172 else
173 if (o->active == ACTIVE_NETWORK)
174 bits |= E5_FULLUPDATE;
175 return bits;
176}
177
178void EntityState5_WriteUpdate(int number, const entity_state_t *s, int changedbits, sizebuf_t *msg)
179{
180 prvm_prog_t *prog = SVVM_prog;
181 unsigned int bits = 0;
182 //model_t *model;
183
184 if (s->active != ACTIVE_NETWORK)
185 {
187 MSG_WriteShort(msg, number | 0x8000);
189 }
190 else
191 {
192 if (PRVM_serveredictfunction((&prog->edicts[s->number]), SendEntity))
193 return;
194
195 bits = changedbits;
196 if ((bits & E5_ORIGIN) && (!(s->flags & RENDER_LOWPRECISION) || s->exteriormodelforclient || s->tagentity || s->viewmodelforclient || (s->number >= 1 && s->number <= svs.maxclients) || s->origin[0] <= -4096.0625 || s->origin[0] >= 4095.9375 || s->origin[1] <= -4096.0625 || s->origin[1] >= 4095.9375 || s->origin[2] <= -4096.0625 || s->origin[2] >= 4095.9375))
197 // maybe also add: ((model = SV_GetModelByIndex(s->modelindex)) != NULL && model->name[0] == '*')
198 bits |= E5_ORIGIN32;
199 // possible values:
200 // negative origin:
201 // (int)(f * 8 - 0.5) >= -32768
202 // (f * 8 - 0.5) > -32769
203 // f > -4096.0625
204 // positive origin:
205 // (int)(f * 8 + 0.5) <= 32767
206 // (f * 8 + 0.5) < 32768
207 // f * 8 + 0.5) < 4095.9375
208 if ((bits & E5_ANGLES) && !(s->flags & RENDER_LOWPRECISION))
209 bits |= E5_ANGLES16;
210 if ((bits & E5_MODEL) && s->modelindex >= 256)
211 bits |= E5_MODEL16;
212 if ((bits & E5_FRAME) && s->frame >= 256)
213 bits |= E5_FRAME16;
214 if (bits & E5_EFFECTS)
215 {
216 if (s->effects & 0xFFFF0000)
217 bits |= E5_EFFECTS32;
218 else if (s->effects & 0xFFFFFF00)
219 bits |= E5_EFFECTS16;
220 }
221 if (bits >= 256)
222 bits |= E5_EXTEND1;
223 if (bits >= 65536)
224 bits |= E5_EXTEND2;
225 if (bits >= 16777216)
226 bits |= E5_EXTEND3;
227 {
228 ENTITYSIZEPROFILING_START(msg, s->number, bits);
229 MSG_WriteShort(msg, number);
230 MSG_WriteByte(msg, bits & 0xFF);
231 if (bits & E5_EXTEND1)
232 MSG_WriteByte(msg, (bits >> 8) & 0xFF);
233 if (bits & E5_EXTEND2)
234 MSG_WriteByte(msg, (bits >> 16) & 0xFF);
235 if (bits & E5_EXTEND3)
236 MSG_WriteByte(msg, (bits >> 24) & 0xFF);
237 if (bits & E5_FLAGS)
238 MSG_WriteByte(msg, s->flags);
239 if (bits & E5_ORIGIN)
240 {
241 if (bits & E5_ORIGIN32)
242 {
243 MSG_WriteCoord32f(msg, s->origin[0]);
244 MSG_WriteCoord32f(msg, s->origin[1]);
245 MSG_WriteCoord32f(msg, s->origin[2]);
246 }
247 else
248 {
249 MSG_WriteCoord13i(msg, s->origin[0]);
250 MSG_WriteCoord13i(msg, s->origin[1]);
251 MSG_WriteCoord13i(msg, s->origin[2]);
252 }
253 }
254 if (bits & E5_ANGLES)
255 {
256 if (bits & E5_ANGLES16)
257 {
258 MSG_WriteAngle16i(msg, s->angles[0]);
259 MSG_WriteAngle16i(msg, s->angles[1]);
260 MSG_WriteAngle16i(msg, s->angles[2]);
261 }
262 else
263 {
264 MSG_WriteAngle8i(msg, s->angles[0]);
265 MSG_WriteAngle8i(msg, s->angles[1]);
266 MSG_WriteAngle8i(msg, s->angles[2]);
267 }
268 }
269 if (bits & E5_MODEL)
270 {
271 if (bits & E5_MODEL16)
272 MSG_WriteShort(msg, s->modelindex);
273 else
274 MSG_WriteByte(msg, s->modelindex);
275 }
276 if (bits & E5_FRAME)
277 {
278 if (bits & E5_FRAME16)
279 MSG_WriteShort(msg, s->frame);
280 else
281 MSG_WriteByte(msg, s->frame);
282 }
283 if (bits & E5_SKIN)
284 MSG_WriteByte(msg, s->skin);
285 if (bits & E5_EFFECTS)
286 {
287 if (bits & E5_EFFECTS32)
288 MSG_WriteLong(msg, s->effects);
289 else if (bits & E5_EFFECTS16)
290 MSG_WriteShort(msg, s->effects);
291 else
292 MSG_WriteByte(msg, s->effects);
293 }
294 if (bits & E5_ALPHA)
295 MSG_WriteByte(msg, s->alpha);
296 if (bits & E5_SCALE)
297 MSG_WriteByte(msg, s->scale);
298 if (bits & E5_COLORMAP)
299 MSG_WriteByte(msg, s->colormap);
300 if (bits & E5_ATTACHMENT)
301 {
302 MSG_WriteShort(msg, s->tagentity);
303 MSG_WriteByte(msg, s->tagindex);
304 }
305 if (bits & E5_LIGHT)
306 {
307 MSG_WriteShort(msg, s->light[0]);
308 MSG_WriteShort(msg, s->light[1]);
309 MSG_WriteShort(msg, s->light[2]);
310 MSG_WriteShort(msg, s->light[3]);
311 MSG_WriteByte(msg, s->lightstyle);
312 MSG_WriteByte(msg, s->lightpflags);
313 }
314 if (bits & E5_GLOW)
315 {
316 MSG_WriteByte(msg, s->glowsize);
317 MSG_WriteByte(msg, s->glowcolor);
318 }
319 if (bits & E5_COLORMOD)
320 {
321 MSG_WriteByte(msg, s->colormod[0]);
322 MSG_WriteByte(msg, s->colormod[1]);
323 MSG_WriteByte(msg, s->colormod[2]);
324 }
325 if (bits & E5_GLOWMOD)
326 {
327 MSG_WriteByte(msg, s->glowmod[0]);
328 MSG_WriteByte(msg, s->glowmod[1]);
329 MSG_WriteByte(msg, s->glowmod[2]);
330 }
331 if (bits & E5_COMPLEXANIMATION)
332 {
334 {
335 int numbones = s->skeletonobject.model->num_bones;
336 int bonenum;
337 short pose7s[7];
338 MSG_WriteByte(msg, 4);
339 MSG_WriteShort(msg, s->modelindex);
340 MSG_WriteByte(msg, numbones);
341 for (bonenum = 0;bonenum < numbones;bonenum++)
342 {
344 MSG_WriteShort(msg, pose7s[0]);
345 MSG_WriteShort(msg, pose7s[1]);
346 MSG_WriteShort(msg, pose7s[2]);
347 MSG_WriteShort(msg, pose7s[3]);
348 MSG_WriteShort(msg, pose7s[4]);
349 MSG_WriteShort(msg, pose7s[5]);
350 MSG_WriteShort(msg, pose7s[6]);
351 }
352 }
353 else
354 {
356 if (s->framegroupblend[3].lerp > 0)
357 {
358 MSG_WriteByte(msg, 3);
367 MSG_WriteByte(msg, s->framegroupblend[0].lerp * 255.0f);
368 MSG_WriteByte(msg, s->framegroupblend[1].lerp * 255.0f);
369 MSG_WriteByte(msg, s->framegroupblend[2].lerp * 255.0f);
370 MSG_WriteByte(msg, s->framegroupblend[3].lerp * 255.0f);
371 }
372 else if (s->framegroupblend[2].lerp > 0)
373 {
374 MSG_WriteByte(msg, 2);
381 MSG_WriteByte(msg, s->framegroupblend[0].lerp * 255.0f);
382 MSG_WriteByte(msg, s->framegroupblend[1].lerp * 255.0f);
383 MSG_WriteByte(msg, s->framegroupblend[2].lerp * 255.0f);
384 }
385 else if (s->framegroupblend[1].lerp > 0)
386 {
387 MSG_WriteByte(msg, 1);
392 MSG_WriteByte(msg, s->framegroupblend[0].lerp * 255.0f);
393 MSG_WriteByte(msg, s->framegroupblend[1].lerp * 255.0f);
394 }
395 else
396 {
397 MSG_WriteByte(msg, 0);
400 }
401 }
402 }
403 if (bits & E5_TRAILEFFECTNUM)
405 ENTITYSIZEPROFILING_END(msg, s->number, bits);
406 }
407 }
408}
409
410qbool EntityFrame5_WriteFrame(sizebuf_t *msg, int maxsize, entityframe5_database_t *d, int numstates, const entity_state_t **states, int viewentnum, unsigned int movesequence, qbool need_empty)
411{
412 prvm_prog_t *prog = SVVM_prog;
413 const entity_state_t *n;
414 int i, num, l, framenum, packetlognumber, priority;
416 unsigned char data[128];
417 entityframe5_packetlog_t *packetlog;
418
419 if (prog->max_edicts > d->maxedicts)
421
422 framenum = d->latestframenum + 1;
423 d->viewentnum = viewentnum;
424
425 // if packet log is full, mark all frames as lost, this will cause
426 // it to send the lost data again
427 for (packetlognumber = 0;packetlognumber < ENTITYFRAME5_MAXPACKETLOGS;packetlognumber++)
428 if (d->packetlog[packetlognumber].packetnumber == 0)
429 break;
430 if (packetlognumber == ENTITYFRAME5_MAXPACKETLOGS)
431 {
432 Con_DPrintf("EntityFrame5_WriteFrame: packetlog overflow for a client, resetting\n");
433 EntityFrame5_LostFrame(d, framenum);
434 packetlognumber = 0;
435 }
436
437 // prepare the buffer
438 memset(&buf, 0, sizeof(buf));
439 buf.data = data;
440 buf.maxsize = sizeof(data);
441
442 // detect changes in states
443 num = 1;
444 for (i = 0;i < numstates;i++)
445 {
446 n = states[i];
447 // mark gaps in entity numbering as removed entities
448 for (;num < n->number;num++)
449 {
450 // if the entity used to exist, clear it
451 if (CHECKPVSBIT(d->visiblebits, num))
452 {
453 CLEARPVSBIT(d->visiblebits, num);
454 d->deltabits[num] = E5_FULLUPDATE;
455 d->priorities[num] = max(d->priorities[num], 8); // removal is cheap
456 d->states[num] = defaultstate;
457 d->states[num].number = num;
458 }
459 }
460 // update the entity state data
461 if (!CHECKPVSBIT(d->visiblebits, num))
462 {
463 // entity just spawned in, don't let it completely hog priority
464 // because of being ancient on the first frame
465 d->updateframenum[num] = framenum;
466 // initial priority is a bit high to make projectiles send on the
467 // first frame, among other things
468 d->priorities[num] = max(d->priorities[num], 4);
469 }
470 SETPVSBIT(d->visiblebits, num);
471 d->deltabits[num] |= EntityState5_DeltaBits(d->states + num, n);
472 d->priorities[num] = max(d->priorities[num], 1);
473 d->states[num] = *n;
474 d->states[num].number = num;
475 // advance to next entity so the next iteration doesn't immediately remove it
476 num++;
477 }
478 // all remaining entities are dead
479 for (;num < d->maxedicts;num++)
480 {
481 if (CHECKPVSBIT(d->visiblebits, num))
482 {
483 CLEARPVSBIT(d->visiblebits, num);
484 d->deltabits[num] = E5_FULLUPDATE;
485 d->priorities[num] = max(d->priorities[num], 8); // removal is cheap
486 d->states[num] = defaultstate;
487 d->states[num].number = num;
488 }
489 }
490
491 // if there isn't at least enough room for an empty svc_entities,
492 // don't bother trying...
493 if (buf.cursize + 11 > buf.maxsize)
494 return false;
495
496 // build lists of entities by priority level
497 memset(d->prioritychaincounts, 0, sizeof(d->prioritychaincounts));
498 l = 0;
499 for (num = 0;num < d->maxedicts;num++)
500 {
501 if (d->priorities[num])
502 {
503 if (d->deltabits[num])
504 {
505 if (d->priorities[num] < (ENTITYFRAME5_PRIORITYLEVELS - 1))
506 d->priorities[num] = EntityState5_Priority(d, num);
507 l = num;
508 priority = d->priorities[num];
510 d->prioritychains[priority][d->prioritychaincounts[priority]++] = num;
511 }
512 else
513 d->priorities[num] = 0;
514 }
515 }
516
517 packetlog = NULL;
518 // write stat updates
520 {
521 for (i = 0;i < MAX_CL_STATS && msg->cursize + 6 + 11 <= maxsize;i++)
522 {
523 if (host_client->statsdeltabits[i>>3] & (1<<(i&7)))
524 {
525 host_client->statsdeltabits[i>>3] &= ~(1<<(i&7));
526 // add packetlog entry now that we have something for it
527 if (!packetlog)
528 {
529 packetlog = d->packetlog + packetlognumber;
530 packetlog->packetnumber = framenum;
531 packetlog->numstates = 0;
532 memset(packetlog->statsdeltabits, 0, sizeof(packetlog->statsdeltabits));
533 }
534 packetlog->statsdeltabits[i>>3] |= (1<<(i&7));
535 if (host_client->stats[i] >= 0 && host_client->stats[i] < 256)
536 {
538 MSG_WriteByte(msg, i);
540 l = 1;
541 }
542 else
543 {
545 MSG_WriteByte(msg, i);
547 l = 1;
548 }
549 }
550 }
551 }
552
553 // only send empty svc_entities frame if needed
554 if(!l && !need_empty)
555 return false;
556
557 // add packetlog entry now that we have something for it
558 if (!packetlog)
559 {
560 packetlog = d->packetlog + packetlognumber;
561 packetlog->packetnumber = framenum;
562 packetlog->numstates = 0;
563 memset(packetlog->statsdeltabits, 0, sizeof(packetlog->statsdeltabits));
564 }
565
566 // write state updates
568 Con_Printf("send: svc_entities %i\n", framenum);
569 d->latestframenum = framenum;
571 MSG_WriteLong(msg, framenum);
573 MSG_WriteLong(msg, movesequence);
574 for (priority = ENTITYFRAME5_PRIORITYLEVELS - 1;priority >= 0 && packetlog->numstates < ENTITYFRAME5_MAXSTATES;priority--)
575 {
576 for (i = 0;i < d->prioritychaincounts[priority] && packetlog->numstates < ENTITYFRAME5_MAXSTATES;i++)
577 {
578 num = d->prioritychains[priority][i];
579 n = d->states + num;
580 if (d->deltabits[num] & E5_FULLUPDATE)
582 buf.cursize = 0;
583 EntityState5_WriteUpdate(num, n, d->deltabits[num], &buf);
584 // if the entity won't fit, try the next one
585 if (msg->cursize + buf.cursize + 2 > maxsize)
586 continue;
587 // write entity to the packet
588 SZ_Write(msg, buf.data, buf.cursize);
589 // mark age on entity for prioritization
590 d->updateframenum[num] = framenum;
591 // log entity so deltabits can be restored later if lost
592 packetlog->states[packetlog->numstates].number = num;
593 packetlog->states[packetlog->numstates].bits = d->deltabits[num];
594 packetlog->numstates++;
595 // clear deltabits and priority so it won't be sent again
596 d->deltabits[num] = 0;
597 d->priorities[num] = 0;
598 }
599 }
600 MSG_WriteShort(msg, 0x8000);
601
602 return true;
603}
604
606{
607 int i;
609 d = (entityframe5_database_t *)Mem_Alloc(pool, sizeof(*d));
610 d->latestframenum = 0;
611 for (i = 0;i < d->maxedicts;i++)
612 d->states[i] = defaultstate;
613 return d;
614}
615
616static int packetlog5cmp(const void *a_, const void *b_)
617{
620 return a->packetnumber - b->packetnumber;
621}
622
624{
625 int i, j, l, bits;
628 static unsigned char statsdeltabits[(MAX_CL_STATS+7)/8];
629 static int deltabits[MAX_EDICTS];
631
632 for (i = 0, p = d->packetlog;i < ENTITYFRAME5_MAXPACKETLOGS;i++, p++)
633 packetlogs[i] = p;
634 qsort(packetlogs, sizeof(*packetlogs), ENTITYFRAME5_MAXPACKETLOGS, packetlog5cmp);
635
636 memset(deltabits, 0, sizeof(deltabits));
637 memset(statsdeltabits, 0, sizeof(statsdeltabits));
638 for (i = 0; i < ENTITYFRAME5_MAXPACKETLOGS; i++)
639 {
640 p = packetlogs[i];
641
642 if (!p->packetnumber)
643 continue;
644
645 if (p->packetnumber <= framenum)
646 {
647 for (j = 0, s = p->states;j < p->numstates;j++, s++)
648 deltabits[s->number] |= s->bits;
649
650 for (l = 0;l < (MAX_CL_STATS+7)/8;l++)
651 statsdeltabits[l] |= p->statsdeltabits[l];
652
653 p->packetnumber = 0;
654 }
655 else
656 {
657 for (j = 0, s = p->states;j < p->numstates;j++, s++)
658 deltabits[s->number] &= ~s->bits;
659 for (l = 0;l < (MAX_CL_STATS+7)/8;l++)
660 statsdeltabits[l] &= ~p->statsdeltabits[l];
661 }
662 }
663
664 for(i = 0; i < d->maxedicts; ++i)
665 {
666 bits = deltabits[i] & ~d->deltabits[i];
667 if(bits)
668 {
669 d->deltabits[i] |= bits;
670 // if it was a very important update, set priority higher
672 d->priorities[i] = max(d->priorities[i], 4);
673 else
674 d->priorities[i] = max(d->priorities[i], 1);
675 }
676 }
677
678 for (l = 0;l < (MAX_CL_STATS+7)/8;l++)
679 host_client->statsdeltabits[l] |= statsdeltabits[l];
680 // no need to mask out the already-set bits here, as we do not
681 // do that priorities stuff
682}
683
685{
686 int i;
687 // scan for packets made obsolete by this ack and delete them
688 for (i = 0;i < ENTITYFRAME5_MAXPACKETLOGS;i++)
689 if (d->packetlog[i].packetnumber <= framenum)
690 d->packetlog[i].packetnumber = 0;
691}
cvar_t developer_networkentities
Definition cl_parse.c:173
void MSG_WriteCoord32f(sizebuf_t *sb, float f)
Definition com_msg.c:197
void MSG_WriteShort(sizebuf_t *sb, int c)
Definition com_msg.c:138
void MSG_WriteAngle16i(sizebuf_t *sb, float f)
Definition com_msg.c:227
void MSG_WriteLong(sizebuf_t *sb, int c)
Definition com_msg.c:147
void MSG_WriteByte(sizebuf_t *sb, int c)
Definition com_msg.c:130
void MSG_WriteCoord13i(sizebuf_t *sb, float f)
Definition com_msg.c:187
void MSG_WriteAngle8i(sizebuf_t *sb, float f)
Definition com_msg.c:222
void SZ_Write(sizebuf_t *buf, const unsigned char *data, int length)
Definition common.c:72
@ PROTOCOL_DARKPLACES2
various changes
Definition common.h:140
@ PROTOCOL_DARKPLACES4
various changes
Definition common.h:138
@ PROTOCOL_NEHAHRABJP2
same as NEHAHRABJP but with 16bit soundindex
Definition common.h:147
@ PROTOCOL_DARKPLACES3
uses EntityFrame4 entity snapshot encoder/decoder which is broken, this attempted to do partial snaps...
Definition common.h:139
@ PROTOCOL_NEHAHRABJP
same as QUAKEDP but with 16bit modelindex
Definition common.h:146
@ PROTOCOL_DARKPLACES5
uses EntityFrame5 entity snapshot encoder/decoder which is based on a Tribes networking article at ht...
Definition common.h:137
@ PROTOCOL_QUAKEDP
darkplaces extended quake protocol (used by TomazQuake and others), backwards compatible as long as n...
Definition common.h:142
@ PROTOCOL_DARKPLACES6
various changes
Definition common.h:136
@ PROTOCOL_QUAKE
quake (aka netquake/normalquake/nq) protocol
Definition common.h:144
@ PROTOCOL_NEHAHRABJP3
same as NEHAHRABJP2 but with some changes
Definition common.h:148
@ PROTOCOL_NEHAHRAMOVIE
Nehahra movie protocol, a big nasty hack dating back to early days of the Quake Standards Group (but ...
Definition common.h:143
@ PROTOCOL_DARKPLACES1
uses EntityFrame entity snapshot encoder/decoder which is a QuakeWorld-like entity snapshot delta com...
Definition common.h:141
void Con_DPrintf(const char *fmt,...)
A Con_Printf that only shows up if the "developer" cvar is set.
Definition console.c:1544
void Con_Printf(const char *fmt,...)
Prints to all appropriate console targets.
Definition console.c:1514
string model
#define n(x, y)
static int(ZEXPORT *qz_inflate)(z_stream *strm
GLsizeiptr const GLvoid * data
Definition glquake.h:639
GLenum GLuint GLenum GLsizei const GLchar * buf
Definition glquake.h:657
#define max(A, B)
Definition mathlib.h:38
#define bound(min, num, max)
Definition mathlib.h:34
#define VectorCompare(a, b)
Definition mathlib.h:113
#define VectorDistance(a, b)
Definition mathlib.h:108
void Matrix4x4_ToBonePose7s(const matrix4x4_t *m, float origininvscale, short *pose7s)
Definition matrixlib.c:1614
float ceil(float f)
#define CLEARPVSBIT(pvs, b)
#define CHECKPVSBIT(pvs, b)
#define SETPVSBIT(pvs, b)
#define PRVM_serveredictfunction(ed, fieldname)
Definition progsvm.h:176
#define SVVM_prog
Definition progsvm.h:766
entity_state_t defaultstate
Definition protocol.c:4
#define E5_EXTEND1
bits >= (1<<8)
Definition protocol.h:763
#define E5_EFFECTS16
short = s->effects
Definition protocol.h:793
#define E5_ATTACHMENT
short = s->tagentity byte = s->tagindex
Definition protocol.h:784
#define E5_FLAGS
byte = s->renderflags
Definition protocol.h:766
#define E5_MODEL
E5_MODEL16=0: byte = s->modelindex E5_MODEL16=1: short = s->modelindex.
Definition protocol.h:751
#define ENTITYSIZEPROFILING_START(msg, num, flags)
Definition protocol.h:39
#define E5_EFFECTS
E5_EFFECTS16=0 && E5_EFFECTS32=0: byte = s->effects E5_EFFECTS16=1 && E5_EFFECTS32=0: short = s->effe...
Definition protocol.h:761
#define E5_MODEL16
flag
Definition protocol.h:776
#define E5_ORIGIN
E5_ORIGIN32=0: short[3] = s->origin[0] * 8, s->origin[1] * 8, s->origin[2] * 8 E5_ORIGIN32=1: float[3...
Definition protocol.h:745
#define E5_COLORMOD
byte[3] = s->colormod[0], s->colormod[1], s->colormod[2]
Definition protocol.h:799
#define E5_COLORMAP
byte = s->colormap
Definition protocol.h:778
#define svc_entities
Definition protocol.h:277
#define E5_EFFECTS32
int = s->effects
Definition protocol.h:795
#define E5_FRAME16
flag
Definition protocol.h:797
#define E5_ORIGIN32
flag
Definition protocol.h:772
#define RENDER_VIEWMODEL
Definition protocol.h:358
#define RENDER_COMPLEXANIMATION
Definition protocol.h:363
#define E5_ANGLES
E5_ANGLES16=0: byte[3] = s->angle[0] * 256 / 360, s->angle[1] * 256 / 360, s->angle[2] * 256 / 360 E5...
Definition protocol.h:748
#define svc_updatestatubyte
Definition protocol.h:270
#define svc_updatestat
Definition protocol.h:217
#define E5_ANGLES16
flag
Definition protocol.h:774
#define E5_SCALE
byte = bound(0, s->scale * 16, 255)
Definition protocol.h:770
#define ENTITYFRAME5_MAXSTATES
Definition protocol.h:827
#define ENTITYSIZEPROFILING_END(msg, num, flags)
Definition protocol.h:42
#define E5_FRAME
E5_FRAME16=0: byte = s->frame E5_FRAME16=1: short = s->frame.
Definition protocol.h:754
#define E5_ALPHA
byte = bound(0, s->alpha * 255, 255)
Definition protocol.h:768
#define E5_LIGHT
short[4] = s->light[0], s->light[1], s->light[2], s->light[3] byte = s->lightstyle byte = s->lightpfl...
Definition protocol.h:788
#define E5_TRAILEFFECTNUM
ushort traileffectnum
Definition protocol.h:813
#define E5_GLOWMOD
byte[3] = s->glowmod[0], s->glowmod[1], s->glowmod[2]
Definition protocol.h:804
#define RENDER_LOWPRECISION
Definition protocol.h:360
#define ENTITYFRAME5_MAXPACKETLOGS
Definition protocol.h:826
#define E5_SKIN
byte = s->skin
Definition protocol.h:756
#define E5_EXTEND2
bits >= (1<<16)
Definition protocol.h:780
#define ENTITYFRAME5_PRIORITYLEVELS
Definition protocol.h:828
#define E5_EXTEND3
bits >= (1<<24)
Definition protocol.h:801
@ ACTIVE_NETWORK
Definition protocol.h:433
#define E5_COMPLEXANIMATION
byte type=0 short frames[1] short times[1] byte type=1 short frames[2] short times[2] byte lerps[2] b...
Definition protocol.h:811
#define E5_FULLUPDATE
reset all entity fields (typically used if status changed)
Definition protocol.h:742
#define E5_GLOW
byte = s->glowsize byte = s->glowcolor
Definition protocol.h:791
int i
#define MAX_EDICTS
max number of objects in game world at once (32768 protocol limit)
Definition qdefs.h:105
#define MAX_CL_STATS
Definition qstats.h:7
#define NULL
Definition qtypes.h:12
bool qbool
Definition qtypes.h:9
server_t sv
local server
Definition sv_main.c:223
model_t * SV_GetModelByIndex(int modelindex)
Definition sv_main.c:1607
mempool_t * sv_mempool
Definition sv_main.c:226
server_static_t svs
persistant server info
Definition sv_main.c:224
client_t * host_client
Definition sv_main.c:29
dp_FragColor b
ret a
int stats[MAX_CL_STATS]
Definition server.h:278
unsigned char statsdeltabits[(MAX_CL_STATS+7)/8]
Definition server.h:277
int integer
Definition cvar.h:73
unsigned char glowmod[3]
Definition protocol.h:472
framegroupblend_t framegroupblend[4]
Definition protocol.h:474
unsigned char flags
Definition protocol.h:468
unsigned char skin
Definition protocol.h:463
unsigned char glowcolor
Definition protocol.h:467
unsigned char glowsize
Definition protocol.h:466
float origin[3]
Definition protocol.h:444
unsigned short tagentity
Definition protocol.h:451
unsigned short viewmodelforclient
Definition protocol.h:453
unsigned char lightstyle
Definition protocol.h:460
unsigned char colormap
Definition protocol.h:462
unsigned short modelindex
Definition protocol.h:449
unsigned char colormod[3]
Definition protocol.h:471
unsigned short traileffectnum
Definition protocol.h:457
skeleton_t skeletonobject
Definition protocol.h:475
unsigned char alpha
Definition protocol.h:464
unsigned short light[4]
Definition protocol.h:458
unsigned short exteriormodelforclient
Definition protocol.h:454
unsigned char tagindex
Definition protocol.h:470
float netcenter[3]
Definition protocol.h:443
float angles[3]
Definition protocol.h:445
unsigned char active
Definition protocol.h:459
unsigned short frame
Definition protocol.h:450
unsigned short number
Definition protocol.h:448
unsigned char scale
Definition protocol.h:465
unsigned char lightpflags
Definition protocol.h:461
int prioritychaincounts[ENTITYFRAME5_PRIORITYLEVELS]
Definition protocol.h:888
unsigned char * visiblebits
Definition protocol.h:872
entityframe5_packetlog_t packetlog[ENTITYFRAME5_MAXPACKETLOGS]
Definition protocol.h:854
unsigned short prioritychains[ENTITYFRAME5_PRIORITYLEVELS][ENTITYFRAME5_MAXSTATES]
Definition protocol.h:889
unsigned char * priorities
Definition protocol.h:863
entity_state_t * states
Definition protocol.h:868
unsigned char statsdeltabits[(MAX_CL_STATS+7)/8]
Definition protocol.h:842
entityframe5_changestate_t states[ENTITYFRAME5_MAXSTATES]
Definition protocol.h:841
prvm_edict_t * edicts
Definition progsvm.h:680
int max_edicts
number of edicts for which space has been (should be) allocated
Definition progsvm.h:673
int maxclients
number of svs.clients slots (updated by maxplayers command)
Definition server.h:28
double time
Definition server.h:76
protocolversion_t protocol
one of the PROTOCOL_ values
Definition server.h:74
int cursize
Definition common.h:54
const struct model_s * model
Definition protocol.h:425
struct matrix4x4_s * relativetransforms
Definition protocol.h:426
qbool EntityFrame5_WriteFrame(sizebuf_t *msg, int maxsize, entityframe5_database_t *d, int numstates, const entity_state_t **states, int viewentnum, unsigned int movesequence, qbool need_empty)
Definition sv_ents5.c:410
entityframe5_database_t * EntityFrame5_AllocDatabase(mempool_t *pool)
Definition sv_ents5.c:605
void EntityFrame5_FreeDatabase(entityframe5_database_t *d)
Definition sv_ents5.c:29
static int EntityState5_DeltaBits(const entity_state_t *o, const entity_state_t *n)
Definition sv_ents5.c:112
static int EntityState5_Priority(entityframe5_database_t *d, int stateindex)
Definition sv_ents5.c:69
static int packetlog5cmp(const void *a_, const void *b_)
Definition sv_ents5.c:616
static double anim_frameduration(model_t *model, int framenum)
Definition sv_ents5.c:20
static void EntityFrame5_ExpandEdicts(entityframe5_database_t *d, int newmax)
Definition sv_ents5.c:38
void EntityFrame5_AckFrame(entityframe5_database_t *d, int framenum)
Definition sv_ents5.c:684
void EntityState5_WriteUpdate(int number, const entity_state_t *s, int changedbits, sizebuf_t *msg)
Definition sv_ents5.c:178
void EntityFrame5_LostFrame(entityframe5_database_t *d, int framenum)
Definition sv_ents5.c:623
static double anim_reducetime(double t, double frameduration, double maxtime)
Definition sv_ents5.c:4
#define Mem_Free(mem)
Definition zone.h:96
#define Mem_Alloc(pool, size)
Definition zone.h:92