1 // Emacs style mode select -*- C++ -*-
2 //-----------------------------------------------------------------------------
6 // Copyright (C) 1993-1996 by id Software, Inc.
8 // This source is available for distribution and/or modification
9 // only under the terms of the DOOM Source Code License as
10 // published by id Software. All rights reserved.
12 // The source is distributed in the hope that it will be useful,
13 // but WITHOUT ANY WARRANTY; without even the implied warranty of
14 // FITNESS FOR A PARTICULAR PURPOSE. See the DOOM Source Code License
20 // Archiving: SaveGame I/O.
22 //-----------------------------------------------------------------------------
25 rcsid[] = "$Id: p_tick.c,v 1.4 1997/02/03 16:47:55 b1 Exp $";
38 // Pads save_p to a 4-byte boundary
39 // so that the load/save works on SGI&Gecko.
40 #define PADSAVEP() save_p += (4 - ((int) save_p & 3)) & 3
47 void P_ArchivePlayers (void)
53 for (i=0 ; i<MAXPLAYERS ; i++)
60 dest = (player_t *)save_p;
61 memcpy (dest,&players[i],sizeof(player_t));
62 save_p += sizeof(player_t);
63 for (j=0 ; j<NUMPSPRITES ; j++)
65 if (dest->psprites[j].state)
67 dest->psprites[j].state
68 = (state_t *)(dest->psprites[j].state-states);
79 void P_UnArchivePlayers (void)
84 for (i=0 ; i<MAXPLAYERS ; i++)
91 memcpy (&players[i],save_p, sizeof(player_t));
92 save_p += sizeof(player_t);
94 // will be set when unarc thinker
96 players[i].message = NULL;
97 players[i].attacker = NULL;
99 for (j=0 ; j<NUMPSPRITES ; j++)
101 if (players[i]. psprites[j].state)
103 players[i]. psprites[j].state
104 = &states[ (int)players[i].psprites[j].state ];
114 void P_ArchiveWorld (void)
123 put = (short *)save_p;
126 for (i=0, sec = sectors ; i<numsectors ; i++,sec++)
128 *put++ = sec->floorheight >> FRACBITS;
129 *put++ = sec->ceilingheight >> FRACBITS;
130 *put++ = sec->floorpic;
131 *put++ = sec->ceilingpic;
132 *put++ = sec->lightlevel;
133 *put++ = sec->special; // needed?
134 *put++ = sec->tag; // needed?
139 for (i=0, li = lines ; i<numlines ; i++,li++)
142 *put++ = li->special;
144 for (j=0 ; j<2 ; j++)
146 if (li->sidenum[j] == -1)
149 si = &sides[li->sidenum[j]];
151 *put++ = si->textureoffset >> FRACBITS;
152 *put++ = si->rowoffset >> FRACBITS;
153 *put++ = si->toptexture;
154 *put++ = si->bottomtexture;
155 *put++ = si->midtexture;
159 save_p = (byte *)put;
167 void P_UnArchiveWorld (void)
176 get = (short *)save_p;
179 for (i=0, sec = sectors ; i<numsectors ; i++,sec++)
181 sec->floorheight = *get++ << FRACBITS;
182 sec->ceilingheight = *get++ << FRACBITS;
183 sec->floorpic = *get++;
184 sec->ceilingpic = *get++;
185 sec->lightlevel = *get++;
186 sec->special = *get++; // needed?
187 sec->tag = *get++; // needed?
188 sec->specialdata = 0;
189 sec->soundtarget = 0;
193 for (i=0, li = lines ; i<numlines ; i++,li++)
196 li->special = *get++;
198 for (j=0 ; j<2 ; j++)
200 if (li->sidenum[j] == -1)
202 si = &sides[li->sidenum[j]];
203 si->textureoffset = *get++ << FRACBITS;
204 si->rowoffset = *get++ << FRACBITS;
205 si->toptexture = *get++;
206 si->bottomtexture = *get++;
207 si->midtexture = *get++;
210 save_p = (byte *)get;
232 void P_ArchiveThinkers (void)
237 // save off the current thinkers
238 for (th = thinkercap.next ; th != &thinkercap ; th=th->next)
240 if (th->function == P_MobjThinker)
244 mobj = (mobj_t *)save_p;
245 memcpy (mobj, th, sizeof(*mobj));
246 save_p += sizeof(*mobj);
247 mobj->state = (state_t *)(mobj->state - states);
250 mobj->player = (player_t *)((mobj->player-players) + 1);
254 // I_Error ("P_ArchiveThinkers: Unknown thinker function");
257 // add a terminating marker
258 *save_p++ = (byte)tc_end;
264 // P_UnArchiveThinkers
266 void P_UnArchiveThinkers (void)
269 thinker_t* currentthinker;
273 // remove all the current thinkers
274 currentthinker = thinkercap.next;
275 while (currentthinker != &thinkercap)
277 next = currentthinker->next;
279 if (currentthinker->function == P_MobjThinker)
280 P_RemoveMobj ((mobj_t *)currentthinker);
282 Z_Free (currentthinker);
284 currentthinker = next;
288 // read in saved thinkers
295 return; // end of list
299 mobj = Z_Malloc (sizeof(*mobj), PU_LEVEL, NULL);
300 memcpy (mobj, save_p, sizeof(*mobj));
301 save_p += sizeof(*mobj);
302 mobj->state = &states[(int)mobj->state];
306 mobj->player = &players[(int)mobj->player-1];
307 mobj->player->mo = mobj;
309 P_SetThingPosition (mobj);
310 mobj->info = &mobjinfo[mobj->type];
311 mobj->floorz = mobj->subsector->sector->floorheight;
312 mobj->ceilingz = mobj->subsector->sector->ceilingheight;
313 mobj->thinker.function = P_MobjThinker;
314 P_AddThinker (&mobj->thinker);
318 I_Error ("Unknown tclass %i in savegame",tclass);
347 // T_MoveCeiling, (ceiling_t: sector_t * swizzle), - active list
348 // T_VerticalDoor, (vldoor_t: sector_t * swizzle),
349 // T_MoveFloor, (floormove_t: sector_t * swizzle),
350 // T_LightFlash, (lightflash_t: sector_t * swizzle),
351 // T_StrobeFlash, (strobe_t: sector_t *),
352 // T_Glow, (glow_t: sector_t *),
353 // T_PlatRaise, (plat_t: sector_t *), - active list
355 void P_ArchiveSpecials (void)
367 // save off the current thinkers
368 for (th = thinkercap.next ; th != &thinkercap ; th=th->next)
370 if (th->function == NULL)
372 for (i = 0; i < MAXCEILINGS;i++)
373 if (activeceilings[i] == (ceiling_t *)th)
378 *save_p++ = tc_ceiling;
380 ceiling = (ceiling_t *)save_p;
381 memcpy (ceiling, th, sizeof(*ceiling));
382 save_p += sizeof(*ceiling);
383 ceiling->sector = (sector_t *)(ceiling->sector - sectors);
388 if (th->function == T_MoveCeiling)
390 *save_p++ = tc_ceiling;
392 ceiling = (ceiling_t *)save_p;
393 memcpy (ceiling, th, sizeof(*ceiling));
394 save_p += sizeof(*ceiling);
395 ceiling->sector = (sector_t *)(ceiling->sector - sectors);
399 if (th->function == T_VerticalDoor)
403 door = (vldoor_t *)save_p;
404 memcpy (door, th, sizeof(*door));
405 save_p += sizeof(*door);
406 door->sector = (sector_t *)(door->sector - sectors);
410 if (th->function == T_MoveFloor)
412 *save_p++ = tc_floor;
414 floor = (floormove_t *)save_p;
415 memcpy (floor, th, sizeof(*floor));
416 save_p += sizeof(*floor);
417 floor->sector = (sector_t *)(floor->sector - sectors);
421 if (th->function == T_PlatRaise)
425 plat = (plat_t *)save_p;
426 memcpy (plat, th, sizeof(*plat));
427 save_p += sizeof(*plat);
428 plat->sector = (sector_t *)(plat->sector - sectors);
432 if (th->function == T_LightFlash)
434 *save_p++ = tc_flash;
436 flash = (lightflash_t *)save_p;
437 memcpy (flash, th, sizeof(*flash));
438 save_p += sizeof(*flash);
439 flash->sector = (sector_t *)(flash->sector - sectors);
443 if (th->function == T_StrobeFlash)
445 *save_p++ = tc_strobe;
447 strobe = (strobe_t *)save_p;
448 memcpy (strobe, th, sizeof(*strobe));
449 save_p += sizeof(*strobe);
450 strobe->sector = (sector_t *)(strobe->sector - sectors);
454 if (th->function == T_Glow)
458 glow = (glow_t *)save_p;
459 memcpy (glow, th, sizeof(*glow));
460 save_p += sizeof(*glow);
461 glow->sector = (sector_t *)(glow->sector - sectors);
466 // add a terminating marker
467 *save_p++ = tc_endspecials;
473 // P_UnArchiveSpecials
475 void P_UnArchiveSpecials (void)
487 // read in saved thinkers
494 return; // end of list
498 ceiling = Z_Malloc (sizeof(*ceiling), PU_LEVEL, NULL);
499 memcpy (ceiling, save_p, sizeof(*ceiling));
500 save_p += sizeof(*ceiling);
501 ceiling->sector = §ors[(int)ceiling->sector];
502 ceiling->sector->specialdata = ceiling;
504 if (ceiling->thinker.function)
505 ceiling->thinker.function = T_MoveCeiling;
507 P_AddThinker (&ceiling->thinker);
508 P_AddActiveCeiling(ceiling);
513 door = Z_Malloc (sizeof(*door), PU_LEVEL, NULL);
514 memcpy (door, save_p, sizeof(*door));
515 save_p += sizeof(*door);
516 door->sector = §ors[(int)door->sector];
517 door->sector->specialdata = door;
518 door->thinker.function = T_VerticalDoor;
519 P_AddThinker (&door->thinker);
524 floor = Z_Malloc (sizeof(*floor), PU_LEVEL, NULL);
525 memcpy (floor, save_p, sizeof(*floor));
526 save_p += sizeof(*floor);
527 floor->sector = §ors[(int)floor->sector];
528 floor->sector->specialdata = floor;
529 floor->thinker.function = T_MoveFloor;
530 P_AddThinker (&floor->thinker);
535 plat = Z_Malloc (sizeof(*plat), PU_LEVEL, NULL);
536 memcpy (plat, save_p, sizeof(*plat));
537 save_p += sizeof(*plat);
538 plat->sector = §ors[(int)plat->sector];
539 plat->sector->specialdata = plat;
541 if (plat->thinker.function)
542 plat->thinker.function = T_PlatRaise;
544 P_AddThinker (&plat->thinker);
545 P_AddActivePlat(plat);
550 flash = Z_Malloc (sizeof(*flash), PU_LEVEL, NULL);
551 memcpy (flash, save_p, sizeof(*flash));
552 save_p += sizeof(*flash);
553 flash->sector = §ors[(int)flash->sector];
554 flash->thinker.function = T_LightFlash;
555 P_AddThinker (&flash->thinker);
560 strobe = Z_Malloc (sizeof(*strobe), PU_LEVEL, NULL);
561 memcpy (strobe, save_p, sizeof(*strobe));
562 save_p += sizeof(*strobe);
563 strobe->sector = §ors[(int)strobe->sector];
564 strobe->thinker.function = T_StrobeFlash;
565 P_AddThinker (&strobe->thinker);
570 glow = Z_Malloc (sizeof(*glow), PU_LEVEL, NULL);
571 memcpy (glow, save_p, sizeof(*glow));
572 save_p += sizeof(*glow);
573 glow->sector = §ors[(int)glow->sector];
574 glow->thinker.function = T_Glow;
575 P_AddThinker (&glow->thinker);
579 I_Error ("P_UnarchiveSpecials:Unknown tclass %i "
580 "in savegame",tclass);