]> icculus.org git repositories - btb/d2x.git/blob - main/netmisc.c
added padding to little-endian version of netgame_info
[btb/d2x.git] / main / netmisc.c
1 /*
2 THE COMPUTER CODE CONTAINED HEREIN IS THE SOLE PROPERTY OF PARALLAX
3 SOFTWARE CORPORATION ("PARALLAX").  PARALLAX, IN DISTRIBUTING THE CODE TO
4 END-USERS, AND SUBJECT TO ALL OF THE TERMS AND CONDITIONS HEREIN, GRANTS A
5 ROYALTY-FREE, PERPETUAL LICENSE TO SUCH END-USERS FOR USE BY SUCH END-USERS
6 IN USING, DISPLAYING,  AND CREATING DERIVATIVE WORKS THEREOF, SO LONG AS
7 SUCH USE, DISPLAY OR CREATION IS FOR NON-COMMERCIAL, ROYALTY OR REVENUE
8 FREE PURPOSES.  IN NO EVENT SHALL THE END-USER USE THE COMPUTER CODE
9 CONTAINED HEREIN FOR REVENUE-BEARING PURPOSES.  THE END-USER UNDERSTANDS
10 AND AGREES TO THE TERMS HEREIN AND ACCEPTS THE SAME BY USE OF THIS FILE.
11 COPYRIGHT 1993-1999 PARALLAX SOFTWARE CORPORATION.  ALL RIGHTS RESERVED.
12 */
13
14 #ifdef HAVE_CONFIG_H
15 #include <conf.h>
16 #endif
17
18 #ifdef RCS
19 static char rcsid[] = "$Id: netmisc.c,v 1.8 2003-10-03 03:19:03 btb Exp $";
20 #endif
21
22 #include <stdio.h>
23 #include <string.h>
24
25 #include "inferno.h"
26 #include "pstypes.h"
27 #include "mono.h"
28
29 #ifdef WORDS_BIGENDIAN
30
31 #include "byteswap.h"
32 #include "segment.h"
33 #include "gameseg.h"
34
35 // routine to calculate the checksum of the segments.  We add these specialized routines
36 // since the current way is byte order dependent.
37
38 void mac_do_checksum_calc(ubyte *b, int len, unsigned int *s1, unsigned int *s2)
39 {
40
41         while(len--)    {
42                 *s1 += *b++;
43                 if (*s1 >= 255 ) *s1 -= 255;
44                 *s2 += *s1;
45         }
46 }
47
48 ushort mac_calc_segment_checksum()
49 {
50         int i, j, k;
51         unsigned int sum1,sum2;
52         short s;
53         int t;
54
55         sum1 = sum2 = 0;
56         for (i = 0; i < Highest_segment_index + 1; i++) {
57                 for (j = 0; j < MAX_SIDES_PER_SEGMENT; j++) {
58                         mac_do_checksum_calc(&(Segments[i].sides[j].type), 1, &sum1, &sum2);
59                         mac_do_checksum_calc(&(Segments[i].sides[j].pad), 1, &sum1, &sum2);
60                         s = INTEL_SHORT(Segments[i].sides[j].wall_num);
61                         mac_do_checksum_calc((ubyte *)&s, 2, &sum1, &sum2);
62                         s = INTEL_SHORT(Segments[i].sides[j].tmap_num);
63                         mac_do_checksum_calc((ubyte *)&s, 2, &sum1, &sum2);
64                         s = INTEL_SHORT(Segments[i].sides[j].tmap_num2);
65                         mac_do_checksum_calc((ubyte *)&s, 2, &sum1, &sum2);
66                         for (k = 0; k < 4; k++) {
67                                 t = INTEL_INT(((int)Segments[i].sides[j].uvls[k].u));
68                                 mac_do_checksum_calc((ubyte *)&t, 4, &sum1, &sum2);
69                                 t = INTEL_INT(((int)Segments[i].sides[j].uvls[k].v));
70                                 mac_do_checksum_calc((ubyte *)&t, 4, &sum1, &sum2);
71                                 t = INTEL_INT(((int)Segments[i].sides[j].uvls[k].l));
72                                 mac_do_checksum_calc((ubyte *)&t, 4, &sum1, &sum2);
73                         }
74                         for (k = 0; k < 2; k++) {
75                                 t = INTEL_INT(((int)Segments[i].sides[j].normals[k].x));
76                                 mac_do_checksum_calc((ubyte *)&t, 4, &sum1, &sum2);
77                                 t = INTEL_INT(((int)Segments[i].sides[j].normals[k].y));
78                                 mac_do_checksum_calc((ubyte *)&t, 4, &sum1, &sum2);
79                                 t = INTEL_INT(((int)Segments[i].sides[j].normals[k].z));
80                                 mac_do_checksum_calc((ubyte *)&t, 4, &sum1, &sum2);
81                         }
82                 }
83                 for (j = 0; j < MAX_SIDES_PER_SEGMENT; j++) {
84                         s = INTEL_SHORT(Segments[i].children[j]);
85                         mac_do_checksum_calc((ubyte *)&s, 2, &sum1, &sum2);
86                 }
87                 for (j = 0; j < MAX_VERTICES_PER_SEGMENT; j++) {
88                         s = INTEL_SHORT(Segments[i].verts[j]);
89                         mac_do_checksum_calc((ubyte *)&s, 2, &sum1, &sum2);
90                 }
91                 t = INTEL_INT(Segments[i].objects);
92                 mac_do_checksum_calc((ubyte *)&t, 4, &sum1, &sum2);
93         }
94         sum2 %= 255;
95         return ((sum1<<8)+ sum2);
96 }
97
98 // this routine totally and completely relies on the fact that the network
99 //  checksum must be calculated on the segments!!!!!
100
101 ushort netmisc_calc_checksum( void * vptr, int len )
102 {
103         vptr = vptr;
104         len = len;
105         return mac_calc_segment_checksum();
106 }
107
108 // following are routine for macintosh only that will swap the elements of
109 // structures send through the networking code.  The structures and
110 // this code must be kept in total sync
111
112 #include "ipx.h"
113 #include "multi.h"
114 #ifdef NETWORK
115 #include "network.h"
116 #endif
117 #include "object.h"
118 #include "powerup.h"
119 #include "error.h"
120
121 byte out_buffer[IPX_MAX_DATA_SIZE];             // used for tmp netgame packets as well as sending object data
122
123 void receive_netplayer_info(ubyte *data, netplayer_info *info)
124 {
125         int loc = 0;
126
127         memcpy(info->callsign, &(data[loc]), CALLSIGN_LEN+1);       loc += CALLSIGN_LEN+1;
128         memcpy(&(info->network.ipx.server), &(data[loc]), 4);       loc += 4;
129         memcpy(&(info->network.ipx.node), &(data[loc]), 6);         loc += 6;
130         info->version_major = data[loc];                            loc++;
131         info->version_minor = data[loc];                            loc++;
132         memcpy(&(info->computer_type), &(data[loc]), 1);            loc++;      // memcpy to avoid compile time warning about enum
133         info->connected = data[loc];                                loc++;
134         memcpy(&(info->socket), &(data[loc]), 2);                   loc += 2;
135         memcpy (&(info->rank),&(data[loc]),1);                      loc++;
136 //MWA  don't think we need to swap this because we need it in high order    info->socket = INTEL_SHORT(info->socket);
137 }
138
139 void send_netplayers_packet(ubyte *server, ubyte *node)
140 {
141         int i, tmpi;
142         int loc = 0;
143         short tmps;
144         
145         memset(out_buffer, 0, sizeof(out_buffer));
146         out_buffer[0] = NetPlayers.type;                                                loc++;
147         tmpi = INTEL_INT(NetPlayers.Security);
148         memcpy(&(out_buffer[loc]), &tmpi, 4);                                   loc += 4;
149         for (i = 0; i < MAX_PLAYERS+4; i++) {
150                 memcpy(&(out_buffer[loc]), NetPlayers.players[i].callsign, CALLSIGN_LEN+1);     loc += CALLSIGN_LEN+1;
151                 memcpy(&(out_buffer[loc]), NetPlayers.players[i].network.ipx.server, 4);                                loc += 4;
152                 memcpy(&(out_buffer[loc]), NetPlayers.players[i].network.ipx.node, 6);                                  loc += 6;
153                 memcpy(&(out_buffer[loc]), &(NetPlayers.players[i].version_major), 1);          loc++;
154                 memcpy(&(out_buffer[loc]), &(NetPlayers.players[i].version_minor), 1);          loc++;
155                 memcpy(&(out_buffer[loc]), &(NetPlayers.players[i].computer_type), 1);          loc++;
156                 memcpy(&(out_buffer[loc]), &(NetPlayers.players[i].connected), 1);                      loc++;
157                 tmps = INTEL_SHORT(NetPlayers.players[i].socket);
158                 memcpy(&(out_buffer[loc]), &tmps, 2);                                                                           loc += 2;               
159                 memcpy(&(out_buffer[loc]), &(NetPlayers.players[i].rank), 1);                   loc++;
160         }
161         
162         if ((server == NULL) && (node == NULL))
163                 ipx_send_broadcast_packet_data( out_buffer, loc );
164         else
165                 ipx_send_internetwork_packet_data( out_buffer, loc, server, node);
166
167 }
168
169 void receive_netplayers_packet(ubyte *data, AllNetPlayers_info *pinfo)
170 {
171         int i, loc = 0;
172
173         pinfo->type = data[loc];                                                        loc++;
174         memcpy(&(pinfo->Security), &(data[loc]), 4);            loc += 4;
175         pinfo->Security = INTEL_INT(pinfo->Security);
176         for (i = 0; i < MAX_PLAYERS+4; i++) {
177                 receive_netplayer_info(&(data[loc]), &(pinfo->players[i]));
178                 loc += 26;                      // sizeof(netplayer_info) on the PC
179         }
180 }
181
182 void send_sequence_packet(sequence_packet seq, ubyte *server, ubyte *node, ubyte *net_address)
183 {
184         short tmps;
185         int loc, tmpi;
186
187         loc = 0;
188         memset(out_buffer, 0, sizeof(out_buffer));
189         out_buffer[0] = seq.type;                                                                               loc++;
190         tmpi = INTEL_INT(seq.Security);
191         memcpy(&(out_buffer[loc]), &tmpi, 4);                                                   loc += 4;               loc += 3;
192         memcpy(&(out_buffer[loc]), seq.player.callsign, CALLSIGN_LEN+1);loc += CALLSIGN_LEN+1;
193         memcpy(&(out_buffer[loc]), seq.player.network.ipx.server, 4);                           loc += 4;
194         memcpy(&(out_buffer[loc]), seq.player.network.ipx.node, 6);                                     loc += 6;
195         out_buffer[loc] = seq.player.version_major;                                             loc++;
196         out_buffer[loc] = seq.player.version_minor;                                             loc++;
197         out_buffer[loc] = seq.player.computer_type;                                             loc++;
198         out_buffer[loc] = seq.player.connected;                                                 loc++;
199         tmps = INTEL_SHORT(seq.player.socket);
200         memcpy(&(out_buffer[loc]), &tmps, 2);                                                   loc += 2;
201    out_buffer[loc]=seq.player.rank;                                                                     loc++;          // for pad byte
202         if (net_address != NULL)        
203                 ipx_send_packet_data( out_buffer, loc, server, node, net_address);
204         else if ((server == NULL) && (node == NULL))
205                 ipx_send_broadcast_packet_data( out_buffer, loc );
206         else
207                 ipx_send_internetwork_packet_data( out_buffer, loc, server, node);
208 }
209
210 void receive_sequence_packet(ubyte *data, sequence_packet *seq)
211 {
212         int loc = 0;
213         
214         seq->type = data[0];                                            loc++;
215         memcpy(&(seq->Security), &(data[loc]), 4);      loc += 4;       loc += 3;               // +3 for pad byte
216         seq->Security = INTEL_INT(seq->Security);
217         receive_netplayer_info(&(data[loc]), &(seq->player));
218 }
219
220 void send_netgame_packet(ubyte *server, ubyte *node, ubyte *net_address, int lite_flag)         // lite says shorter netgame packets
221 {
222         uint tmpi;
223         ushort tmps; // p;
224         int i, j;
225         int loc = 0;
226         
227         memset(out_buffer, 0, IPX_MAX_DATA_SIZE);
228         memcpy(&(out_buffer[loc]), &(Netgame.type), 1); loc++;
229         tmpi = INTEL_INT(Netgame.Security);
230         memcpy(&(out_buffer[loc]), &tmpi, 4);           loc += 4;
231         memcpy(&(out_buffer[loc]), Netgame.game_name, NETGAME_NAME_LEN+1); loc += (NETGAME_NAME_LEN+1);
232         memcpy(&(out_buffer[loc]), Netgame.mission_title, MISSION_NAME_LEN+1);  loc += (MISSION_NAME_LEN+1);
233         memcpy(&(out_buffer[loc]), Netgame.mission_name, 9);                    loc += 9;
234         tmpi = INTEL_INT(Netgame.levelnum);
235         memcpy(&(out_buffer[loc]), &tmpi, 4);                                                   loc += 4;
236         memcpy(&(out_buffer[loc]), &(Netgame.gamemode), 1);                             loc++;
237         memcpy(&(out_buffer[loc]), &(Netgame.RefusePlayers), 1);                loc++;
238         memcpy(&(out_buffer[loc]), &(Netgame.difficulty), 1);                   loc++;
239         memcpy(&(out_buffer[loc]), &(Netgame.game_status), 1);                  loc++;
240         memcpy(&(out_buffer[loc]), &(Netgame.numplayers), 1);                   loc++;
241         memcpy(&(out_buffer[loc]), &(Netgame.max_numplayers), 1);               loc++;
242         memcpy(&(out_buffer[loc]), &(Netgame.numconnected), 1);                 loc++;
243         memcpy(&(out_buffer[loc]), &(Netgame.game_flags), 1);                   loc++;
244         memcpy(&(out_buffer[loc]), &(Netgame.protocol_version), 1);             loc++;
245         memcpy(&(out_buffer[loc]), &(Netgame.version_major), 1);                loc++;
246         memcpy(&(out_buffer[loc]), &(Netgame.version_minor), 1);                loc++;
247         memcpy(&(out_buffer[loc]), &(Netgame.team_vector), 1);                  loc++;
248         
249         if (lite_flag)
250                 goto do_send;
251
252 // will this work -- damn bitfields -- totally bogus when trying to do this type of stuff
253 // Watcom makes bitfields from left to right.  CW7 on the mac goes from right to left.
254 // then they are endian swapped
255
256         tmps = *(ushort *)((ubyte *)(&Netgame.team_vector) + 1);                        // get the values for the first short bitfield
257         tmps = INTEL_SHORT(tmps);
258         memcpy(&(out_buffer[loc]), &tmps, 2);           loc += 2;
259
260         tmps = *(ushort *)((ubyte *)(&Netgame.team_vector) + 3);                        // get the values for the second short bitfield
261         tmps = INTEL_SHORT(tmps);
262         memcpy(&(out_buffer[loc]), &tmps, 2);           loc += 2;
263
264 #if 0           // removed since I reordered bitfields on mac
265         p = *(ushort *)((ubyte *)(&Netgame.team_vector) + 1);                   // get the values for the first short bitfield
266         tmps = 0;
267         for (i = 15; i >= 0; i--) {
268                 if ( p & (1 << i) )
269                         tmps |= (1 << (15 - i));
270         }
271         tmps = INTEL_SHORT(tmps);
272         memcpy(&(out_buffer[loc]), &tmps, 2);                                                   loc += 2;
273         p = *(ushort *)((ubyte *)(&Netgame.team_vector) + 3);                   // get the values for the second short bitfield
274         tmps = 0;
275         for (i = 15; i >= 0; i--) {
276                 if ( p & (1 << i) )
277                         tmps |= (1 << (15 - i));
278         }
279         tmps = INTEL_SHORT(tmps);
280         memcpy(&(out_buffer[loc]), &tmps, 2);                                                   loc += 2;
281 #endif
282         
283         memcpy(&(out_buffer[loc]), Netgame.team_name, 2*(CALLSIGN_LEN+1)); loc += 2*(CALLSIGN_LEN+1);
284         for (i = 0; i < MAX_PLAYERS; i++) {
285                 tmpi = INTEL_INT(Netgame.locations[i]);
286                 memcpy(&(out_buffer[loc]), &tmpi, 4); loc += 4;                 // SWAP HERE!!!
287         }
288
289         for (i = 0; i < MAX_PLAYERS; i++) {
290                 for (j = 0; j < MAX_PLAYERS; j++) {
291                         tmps = INTEL_SHORT(Netgame.kills[i][j]);
292                         memcpy(&(out_buffer[loc]), &tmps, 2); loc += 2;                 // SWAP HERE!!!
293                 }
294         }
295
296         tmps = INTEL_SHORT(Netgame.segments_checksum);
297         memcpy(&(out_buffer[loc]), &tmps, 2); loc += 2;                         // SWAP_HERE
298         tmps = INTEL_SHORT(Netgame.team_kills[0]);
299         memcpy(&(out_buffer[loc]), &tmps, 2); loc += 2;                         // SWAP_HERE
300         tmps = INTEL_SHORT(Netgame.team_kills[1]);
301         memcpy(&(out_buffer[loc]), &tmps, 2); loc += 2;                         // SWAP_HERE
302         for (i = 0; i < MAX_PLAYERS; i++) {
303                 tmps = INTEL_SHORT(Netgame.killed[i]);
304                 memcpy(&(out_buffer[loc]), &tmps, 2); loc += 2;                 // SWAP HERE!!!
305         }
306         for (i = 0; i < MAX_PLAYERS; i++) {
307                 tmps = INTEL_SHORT(Netgame.player_kills[i]);
308                 memcpy(&(out_buffer[loc]), &tmps, 2); loc += 2;                 // SWAP HERE!!!
309         }
310
311         tmpi = INTEL_INT(Netgame.KillGoal);
312         memcpy(&(out_buffer[loc]), &tmpi, 4); loc += 4;                         // SWAP_HERE
313         tmpi = INTEL_INT(Netgame.PlayTimeAllowed);
314         memcpy(&(out_buffer[loc]), &tmpi, 4); loc += 4;                         // SWAP_HERE
315         tmpi = INTEL_INT(Netgame.level_time);
316         memcpy(&(out_buffer[loc]), &tmpi, 4); loc += 4;                         // SWAP_HERE
317         tmpi = INTEL_INT(Netgame.control_invul_time);
318         memcpy(&(out_buffer[loc]), &tmpi, 4); loc += 4;                         // SWAP_HERE
319         tmpi = INTEL_INT(Netgame.monitor_vector);
320         memcpy(&(out_buffer[loc]), &tmpi, 4); loc += 4;                         // SWAP_HERE
321         for (i = 0; i < MAX_PLAYERS; i++) {
322                 tmpi = INTEL_INT(Netgame.player_score[i]);
323                 memcpy(&(out_buffer[loc]), &tmpi, 4); loc += 4;                         // SWAP_HERE
324         }
325         for (i = 0; i < MAX_PLAYERS; i++) {
326                 memcpy(&(out_buffer[loc]), &(Netgame.player_flags[i]), 1); loc++;
327         }
328         tmps = INTEL_SHORT(Netgame.PacketsPerSec);
329         memcpy(&(out_buffer[loc]), &tmps, 2);                                   loc += 2;
330         memcpy(&(out_buffer[loc]), &(Netgame.ShortPackets), 1); loc ++;
331
332 do_send:
333         if (net_address != NULL)        
334                 ipx_send_packet_data( out_buffer, loc, server, node, net_address);
335         else if ((server == NULL) && (node == NULL))
336                 ipx_send_broadcast_packet_data( out_buffer, loc );
337         else
338                 ipx_send_internetwork_packet_data( out_buffer, loc, server, node);
339 }
340
341 void receive_netgame_packet(ubyte *data, netgame_info *netgame, int lite_flag)
342 {
343         int i, j;
344         int loc = 0;
345         short bitfield; // new_field;
346         
347         memcpy(&(netgame->type), &(data[loc]), 1);                                              loc++;
348         memcpy(&(netgame->Security), &(data[loc]), 4);                                  loc += 4;
349         netgame->Security = INTEL_INT(netgame->Security);
350         memcpy(netgame->game_name, &(data[loc]), NETGAME_NAME_LEN+1);   loc += (NETGAME_NAME_LEN+1);
351         memcpy(netgame->mission_title, &(data[loc]), MISSION_NAME_LEN+1); loc += (MISSION_NAME_LEN+1);
352         memcpy(netgame->mission_name, &(data[loc]), 9);                                 loc += 9;
353         memcpy(&(netgame->levelnum), &(data[loc]), 4);                                  loc += 4;
354         netgame->levelnum = INTEL_INT(netgame->levelnum);
355         memcpy(&(netgame->gamemode), &(data[loc]), 1);                                  loc++;
356         memcpy(&(netgame->RefusePlayers), &(data[loc]), 1);                             loc++;
357         memcpy(&(netgame->difficulty), &(data[loc]), 1);                                loc++;
358         memcpy(&(netgame->game_status), &(data[loc]), 1);                               loc++;
359         memcpy(&(netgame->numplayers), &(data[loc]), 1);                                loc++;
360         memcpy(&(netgame->max_numplayers), &(data[loc]), 1);                    loc++;
361         memcpy(&(netgame->numconnected), &(data[loc]), 1);                              loc++;
362         memcpy(&(netgame->game_flags), &(data[loc]), 1);                                loc++;
363         memcpy(&(netgame->protocol_version), &(data[loc]), 1);                  loc++;
364         memcpy(&(netgame->version_major), &(data[loc]), 1);                             loc++;
365         memcpy(&(netgame->version_minor), &(data[loc]), 1);                             loc++;
366         memcpy(&(netgame->team_vector), &(data[loc]), 1);                               loc++;
367
368         if (lite_flag)
369                 return;
370
371         memcpy(&bitfield, &(data[loc]), 2);     loc += 2;
372         bitfield = INTEL_SHORT(bitfield);
373         memcpy(((ubyte *)(&netgame->team_vector) + 1), &bitfield, 2);
374
375         memcpy(&bitfield, &(data[loc]), 2);     loc += 2;
376         bitfield = INTEL_SHORT(bitfield);
377         memcpy(((ubyte *)(&netgame->team_vector) + 3), &bitfield, 2);
378
379 #if 0           // not used since reordering mac bitfields
380         memcpy(&bitfield, &(data[loc]), 2);                                                             loc += 2;
381         new_field = 0;
382         for (i = 15; i >= 0; i--) {
383                 if ( bitfield & (1 << i) )
384                         new_field |= (1 << (15 - i));
385         }
386         new_field = INTEL_SHORT(new_field);
387         memcpy(((ubyte *)(&netgame->team_vector) + 1), &new_field, 2);
388
389         memcpy(&bitfield, &(data[loc]), 2);                                                             loc += 2;
390         new_field = 0;
391         for (i = 15; i >= 0; i--) {
392                 if ( bitfield & (1 << i) )
393                         new_field |= (1 << (15 - i));
394         }
395         new_field = INTEL_SHORT(new_field);
396         memcpy(((ubyte *)(&netgame->team_vector) + 3), &new_field, 2);
397 #endif
398
399         memcpy(netgame->team_name, &(data[loc]), 2*(CALLSIGN_LEN+1));           loc += 2*(CALLSIGN_LEN+1);
400         for (i = 0; i < MAX_PLAYERS; i++) {
401                 memcpy(&(netgame->locations[i]), &(data[loc]), 4);                              loc += 4;
402                 netgame->locations[i] = INTEL_INT(netgame->locations[i]);
403         }
404
405         for (i = 0; i < MAX_PLAYERS; i++) {
406                 for (j = 0; j < MAX_PLAYERS; j++) {
407                         memcpy(&(netgame->kills[i][j]), &(data[loc]), 2);                       loc += 2;
408                         netgame->kills[i][j] = INTEL_SHORT(netgame->kills[i][j]);
409                 }
410         }
411
412         memcpy(&(netgame->segments_checksum), &(data[loc]), 2);                         loc += 2;
413         netgame->segments_checksum = INTEL_SHORT(netgame->segments_checksum);
414         memcpy(&(netgame->team_kills[0]), &(data[loc]), 2);                             loc += 2;
415         netgame->team_kills[0] = INTEL_SHORT(netgame->team_kills[0]);
416         memcpy(&(netgame->team_kills[1]), &(data[loc]), 2);                                     loc += 2;
417         netgame->team_kills[1] = INTEL_SHORT(netgame->team_kills[1]);
418         for (i = 0; i < MAX_PLAYERS; i++) {
419                 memcpy(&(netgame->killed[i]), &(data[loc]), 2);                                 loc += 2;
420                 netgame->killed[i] = INTEL_SHORT(netgame->killed[i]);
421         }
422         for (i = 0; i < MAX_PLAYERS; i++) {
423                 memcpy(&(netgame->player_kills[i]), &(data[loc]), 2);                   loc += 2;
424                 netgame->player_kills[i] = INTEL_SHORT(netgame->player_kills[i]);
425         }
426         memcpy(&(netgame->KillGoal), &(data[loc]), 4);                                          loc += 4;
427         netgame->KillGoal = INTEL_INT(netgame->KillGoal);
428         memcpy(&(netgame->PlayTimeAllowed), &(data[loc]), 4);                           loc += 4;
429         netgame->PlayTimeAllowed = INTEL_INT(netgame->PlayTimeAllowed);
430
431         memcpy(&(netgame->level_time), &(data[loc]), 4);                                        loc += 4;
432         netgame->level_time = INTEL_INT(netgame->level_time);
433         memcpy(&(netgame->control_invul_time), &(data[loc]), 4);                        loc += 4;
434         netgame->control_invul_time = INTEL_INT(netgame->control_invul_time);
435         memcpy(&(netgame->monitor_vector), &(data[loc]), 4);                            loc += 4;
436         netgame->monitor_vector = INTEL_INT(netgame->monitor_vector);
437         for (i = 0; i < MAX_PLAYERS; i++) {
438                 memcpy(&(netgame->player_score[i]), &(data[loc]), 4);                   loc += 4;
439                 netgame->player_score[i] = INTEL_INT(netgame->player_score[i]);
440         }
441         for (i = 0; i < MAX_PLAYERS; i++) {
442                 memcpy(&(netgame->player_flags[i]), &(data[loc]), 1); loc++;
443         }
444         memcpy(&(netgame->PacketsPerSec), &(data[loc]), 2);                                     loc += 2;
445         netgame->PacketsPerSec = INTEL_SHORT(netgame->PacketsPerSec);
446         memcpy(&(netgame->ShortPackets), &(data[loc]), 1);                                      loc ++;
447
448 }
449
450 void swap_object(object *obj)
451 {
452 // swap the short and int entries for this object
453         obj->signature                  = INTEL_INT(obj->signature);
454         obj->next                               = INTEL_SHORT(obj->next);
455         obj->prev                               = INTEL_SHORT(obj->prev);
456         obj->segnum                             = INTEL_SHORT(obj->segnum);
457         obj->pos.x                              = INTEL_INT(obj->pos.x);
458         obj->pos.y                              = INTEL_INT(obj->pos.y);
459         obj->pos.z                              = INTEL_INT(obj->pos.z);
460
461         obj->orient.rvec.x              = INTEL_INT(obj->orient.rvec.x);
462         obj->orient.rvec.y              = INTEL_INT(obj->orient.rvec.y);
463         obj->orient.rvec.z              = INTEL_INT(obj->orient.rvec.z);
464         obj->orient.fvec.x              = INTEL_INT(obj->orient.fvec.x);
465         obj->orient.fvec.y              = INTEL_INT(obj->orient.fvec.y);
466         obj->orient.fvec.z              = INTEL_INT(obj->orient.fvec.z);
467         obj->orient.uvec.x              = INTEL_INT(obj->orient.uvec.x);
468         obj->orient.uvec.y              = INTEL_INT(obj->orient.uvec.y);
469         obj->orient.uvec.z              = INTEL_INT(obj->orient.uvec.z);
470         
471         obj->size                               = INTEL_INT(obj->size);
472         obj->shields                    = INTEL_INT(obj->shields);
473         
474         obj->last_pos.x                 = INTEL_INT(obj->last_pos.x);
475         obj->last_pos.y                 = INTEL_INT(obj->last_pos.y);
476         obj->last_pos.z                 = INTEL_INT(obj->last_pos.z);
477         
478         obj->lifeleft                   = INTEL_INT(obj->lifeleft);
479         
480         switch (obj->movement_type) {
481         
482         case MT_PHYSICS:
483         
484                 obj->mtype.phys_info.velocity.x = INTEL_INT(obj->mtype.phys_info.velocity.x);
485                 obj->mtype.phys_info.velocity.y = INTEL_INT(obj->mtype.phys_info.velocity.y);
486                 obj->mtype.phys_info.velocity.z = INTEL_INT(obj->mtype.phys_info.velocity.z);
487         
488                 obj->mtype.phys_info.thrust.x   = INTEL_INT(obj->mtype.phys_info.thrust.x);
489                 obj->mtype.phys_info.thrust.y   = INTEL_INT(obj->mtype.phys_info.thrust.y);
490                 obj->mtype.phys_info.thrust.z   = INTEL_INT(obj->mtype.phys_info.thrust.z);
491         
492                 obj->mtype.phys_info.mass               = INTEL_INT(obj->mtype.phys_info.mass);
493                 obj->mtype.phys_info.drag               = INTEL_INT(obj->mtype.phys_info.drag);
494                 obj->mtype.phys_info.brakes             = INTEL_INT(obj->mtype.phys_info.brakes);
495         
496                 obj->mtype.phys_info.rotvel.x   = INTEL_INT(obj->mtype.phys_info.rotvel.x);
497                 obj->mtype.phys_info.rotvel.y   = INTEL_INT(obj->mtype.phys_info.rotvel.y);
498                 obj->mtype.phys_info.rotvel.z   = INTEL_INT(obj->mtype.phys_info.rotvel.z);
499         
500                 obj->mtype.phys_info.rotthrust.x = INTEL_INT(obj->mtype.phys_info.rotthrust.x);
501                 obj->mtype.phys_info.rotthrust.y = INTEL_INT(obj->mtype.phys_info.rotthrust.y);
502                 obj->mtype.phys_info.rotthrust.z = INTEL_INT(obj->mtype.phys_info.rotthrust.z);
503         
504                 obj->mtype.phys_info.turnroll   = INTEL_INT(obj->mtype.phys_info.turnroll);
505                 obj->mtype.phys_info.flags              = INTEL_SHORT(obj->mtype.phys_info.flags);
506         
507                 break;
508         
509         case MT_SPINNING:
510                 
511                 obj->mtype.spin_rate.x = INTEL_INT(obj->mtype.spin_rate.x);
512                 obj->mtype.spin_rate.y = INTEL_INT(obj->mtype.spin_rate.y);
513                 obj->mtype.spin_rate.z = INTEL_INT(obj->mtype.spin_rate.z);
514                 break;
515         }
516         
517         switch (obj->control_type) {
518         
519         case CT_WEAPON:
520                 obj->ctype.laser_info.parent_type               = INTEL_SHORT(obj->ctype.laser_info.parent_type);
521                 obj->ctype.laser_info.parent_num                = INTEL_SHORT(obj->ctype.laser_info.parent_num);
522                 obj->ctype.laser_info.parent_signature  = INTEL_INT(obj->ctype.laser_info.parent_signature);
523                 obj->ctype.laser_info.creation_time             = INTEL_INT(obj->ctype.laser_info.creation_time);
524                 obj->ctype.laser_info.last_hitobj               = INTEL_SHORT(obj->ctype.laser_info.last_hitobj);
525                 obj->ctype.laser_info.track_goal                = INTEL_SHORT(obj->ctype.laser_info.track_goal);
526                 obj->ctype.laser_info.multiplier                = INTEL_INT(obj->ctype.laser_info.multiplier);
527                 break;
528         
529         case CT_EXPLOSION:
530                 obj->ctype.expl_info.spawn_time         = INTEL_INT(obj->ctype.expl_info.spawn_time);
531                 obj->ctype.expl_info.delete_time        = INTEL_INT(obj->ctype.expl_info.delete_time);
532                 obj->ctype.expl_info.delete_objnum      = INTEL_SHORT(obj->ctype.expl_info.delete_objnum);
533                 obj->ctype.expl_info.attach_parent      = INTEL_SHORT(obj->ctype.expl_info.attach_parent);
534                 obj->ctype.expl_info.prev_attach        = INTEL_SHORT(obj->ctype.expl_info.prev_attach);
535                 obj->ctype.expl_info.next_attach        = INTEL_SHORT(obj->ctype.expl_info.next_attach);
536                 break;
537         
538         case CT_AI:
539                 obj->ctype.ai_info.hide_segment                 = INTEL_SHORT(obj->ctype.ai_info.hide_segment);
540                 obj->ctype.ai_info.hide_index                   = INTEL_SHORT(obj->ctype.ai_info.hide_index);
541                 obj->ctype.ai_info.path_length                  = INTEL_SHORT(obj->ctype.ai_info.path_length);
542                 obj->ctype.ai_info.danger_laser_num             = INTEL_SHORT(obj->ctype.ai_info.danger_laser_num);
543                 obj->ctype.ai_info.danger_laser_signature = INTEL_INT(obj->ctype.ai_info.danger_laser_signature);
544                 obj->ctype.ai_info.dying_start_time     = INTEL_INT(obj->ctype.ai_info.dying_start_time);
545                 break;
546         
547         case CT_LIGHT:
548                 obj->ctype.light_info.intensity = INTEL_INT(obj->ctype.light_info.intensity);
549                 break;
550         
551         case CT_POWERUP:
552                 obj->ctype.powerup_info.count = INTEL_INT(obj->ctype.powerup_info.count);
553                 obj->ctype.powerup_info.creation_time = INTEL_INT(obj->ctype.powerup_info.creation_time);
554                 //Below commented out 5/2/96 by Matt.  I asked Allender why it was
555                 //here, and he didn't know, and it looks like it doesn't belong.
556                 //if (obj->id == POW_VULCAN_WEAPON)
557                 //      obj->ctype.powerup_info.count = VULCAN_WEAPON_AMMO_AMOUNT;
558                 break;
559         
560         }
561         
562         switch (obj->render_type) {
563         
564         case RT_MORPH:
565         case RT_POLYOBJ: {
566                 int i;
567         
568                 obj->rtype.pobj_info.model_num          = INTEL_INT(obj->rtype.pobj_info.model_num);
569         
570                 for (i=0;i<MAX_SUBMODELS;i++) {
571                         obj->rtype.pobj_info.anim_angles[i].p = INTEL_INT(obj->rtype.pobj_info.anim_angles[i].p);
572                         obj->rtype.pobj_info.anim_angles[i].b = INTEL_INT(obj->rtype.pobj_info.anim_angles[i].b);
573                         obj->rtype.pobj_info.anim_angles[i].h = INTEL_INT(obj->rtype.pobj_info.anim_angles[i].h);
574                 }
575         
576                 obj->rtype.pobj_info.subobj_flags       = INTEL_INT(obj->rtype.pobj_info.subobj_flags);
577                 obj->rtype.pobj_info.tmap_override      = INTEL_INT(obj->rtype.pobj_info.tmap_override);
578                 obj->rtype.pobj_info.alt_textures       = INTEL_INT(obj->rtype.pobj_info.alt_textures);
579                 break;
580         }
581         
582         case RT_WEAPON_VCLIP:
583         case RT_HOSTAGE:
584         case RT_POWERUP:
585         case RT_FIREBALL:
586                 obj->rtype.vclip_info.vclip_num = INTEL_INT(obj->rtype.vclip_info.vclip_num);
587                 obj->rtype.vclip_info.frametime = INTEL_INT(obj->rtype.vclip_info.frametime);
588                 break;
589         
590         case RT_LASER:
591                 break;
592         
593         }
594 //  END OF SWAPPING OBJECT STRUCTURE
595
596 }
597
598 #else /* !WORDS_BIGENDIAN */
599
600
601 // Calculates the checksum of a block of memory.
602 ushort netmisc_calc_checksum( void * vptr, int len )
603 {
604         ubyte * ptr = (ubyte *)vptr;
605         unsigned int sum1,sum2;
606
607         sum1 = sum2 = 0;
608
609         while(len--)    {
610                 sum1 += *ptr++;
611                 if (sum1 >= 255 ) sum1 -= 255;
612                 sum2 += sum1;
613         }
614         sum2 %= 255;
615         
616         return ((sum1<<8)+ sum2);
617 }
618
619 #endif /* WORDS_BIGENDIAN */
620
621 //--unused-- //Finds the difference between block1 and block2.  Fills in diff_buffer and 
622 //--unused-- //returns the size of diff_buffer.
623 //--unused-- int netmisc_find_diff( void *block1, void *block2, int block_size, void *diff_buffer )
624 //--unused-- {
625 //--unused--    int mode;
626 //--unused--    ushort *c1, *c2, *diff_start, *c3;
627 //--unused--    int i, j, size, diff, n , same;
628 //--unused-- 
629 //--unused--    size=(block_size+1)/sizeof(ushort);
630 //--unused--    c1 = (ushort *)block1;
631 //--unused--    c2 = (ushort *)block2;
632 //--unused--    c3 = (ushort *)diff_buffer;
633 //--unused-- 
634 //--unused--    mode = same = diff = n = 0;
635 //--unused-- 
636 //--unused--    //mprintf( 0, "=================================\n" );
637 //--unused-- 
638 //--unused--    for (i=0; i<size; i++, c1++, c2++ )     {
639 //--unused--            if (*c1 != *c2 ) {
640 //--unused--                    if (mode==0)    {
641 //--unused--                            mode = 1;
642 //--unused--                            //mprintf( 0, "%ds ", same );
643 //--unused--                            c3[n++] = same;
644 //--unused--                            same=0; diff=0;
645 //--unused--                            diff_start = c2;
646 //--unused--                    }
647 //--unused--                    *c1 = *c2;
648 //--unused--                    diff++;
649 //--unused--                    if (diff==65535) {
650 //--unused--                            mode = 0;
651 //--unused--                            // send how many diff ones.
652 //--unused--                            //mprintf( 0, "%dd ", diff );
653 //--unused--                            c3[n++]=diff;
654 //--unused--                            // send all the diff ones.
655 //--unused--                            for (j=0; j<diff; j++ )
656 //--unused--                                    c3[n++] = diff_start[j];
657 //--unused--                            same=0; diff=0;
658 //--unused--                            diff_start = c2;
659 //--unused--                    }
660 //--unused--            } else {
661 //--unused--                    if (mode==1)    {
662 //--unused--                            mode=0;
663 //--unused--                            // send how many diff ones.
664 //--unused--                            //mprintf( 0, "%dd ", diff );
665 //--unused--                            c3[n++]=diff;
666 //--unused--                            // send all the diff ones.
667 //--unused--                            for (j=0; j<diff; j++ )
668 //--unused--                                    c3[n++] = diff_start[j];
669 //--unused--                            same=0; diff=0;
670 //--unused--                            diff_start = c2;
671 //--unused--                    }
672 //--unused--                    same++;
673 //--unused--                    if (same==65535)        {
674 //--unused--                            mode=1;
675 //--unused--                            // send how many the same
676 //--unused--                            //mprintf( 0, "%ds ", same );
677 //--unused--                            c3[n++] = same;
678 //--unused--                            same=0; diff=0;
679 //--unused--                            diff_start = c2;
680 //--unused--                    }
681 //--unused--            }
682 //--unused--    
683 //--unused--    }
684 //--unused--    if (mode==0)    {
685 //--unused--            // send how many the same
686 //--unused--            //mprintf( 0, "%ds ", same );
687 //--unused--            c3[n++] = same;
688 //--unused--    } else {
689 //--unused--            // send how many diff ones.
690 //--unused--            //mprintf( 0, "%dd ", diff );
691 //--unused--            c3[n++]=diff;
692 //--unused--            // send all the diff ones.
693 //--unused--            for (j=0; j<diff; j++ )
694 //--unused--                    c3[n++] = diff_start[j];
695 //--unused--    }
696 //--unused-- 
697 //--unused--    //mprintf( 0, "=================================\n" );
698 //--unused--    
699 //--unused--    return n*2;
700 //--unused-- }
701
702 //--unused-- //Applies diff_buffer to block1 to create a new block1.  Returns the final
703 //--unused-- //size of block1.
704 //--unused-- int netmisc_apply_diff(void *block1, void *diff_buffer, int diff_size )    
705 //--unused-- {
706 //--unused--    unsigned int i, j, n, size;
707 //--unused--    ushort *c1, *c2;
708 //--unused-- 
709 //--unused--    //mprintf( 0, "=================================\n" );
710 //--unused--    c1 = (ushort *)diff_buffer;
711 //--unused--    c2 = (ushort *)block1;
712 //--unused-- 
713 //--unused--    size = diff_size/2;
714 //--unused-- 
715 //--unused--    i=j=0;
716 //--unused--    while (1)       {
717 //--unused--            j += c1[i];                     // Same
718 //--unused--            //mprintf( 0, "%ds ", c1[i] );
719 //--unused--            i++;
720 //--unused--            if ( i>=size) break;
721 //--unused--            n = c1[i];                      // ndiff
722 //--unused--            //mprintf( 0, "%dd ", c1[i] );
723 //--unused--            i++;
724 //--unused--            if (n>0)        {
725 //--unused--                    //Assert( n* < 256 );
726 //--unused--                    memcpy( &c2[j], &c1[i], n*2 );
727 //--unused--                    i += n;
728 //--unused--                    j += n;
729 //--unused--            }
730 //--unused--            if ( i>=size) break;
731 //--unused--    }
732 //--unused--    //mprintf( 0, "=================================\n" );
733 //--unused-- 
734 //--unused--    return j*2;
735 //--unused-- }
736