P_ArchiveMisc, P_UnArchiveSPGame: Support overridden roundqueue entries

Will error for overridden material from the future (how did it get overridden?), but accomodates everything before the roundqueue's head.
This commit is contained in:
toaster 2023-11-19 21:57:31 +00:00
parent 6f32a3097c
commit ddf34433dd
2 changed files with 52 additions and 11 deletions

View file

@ -5884,14 +5884,30 @@ static inline void P_ArchiveMisc(savebuffer_t *save)
WRITEUINT8(save->p, roundqueue.roundnum); WRITEUINT8(save->p, roundqueue.roundnum);
UINT8 i; UINT8 i;
UINT16 mapnum;
for (i = 0; i < roundqueue.size; i++) for (i = 0; i < roundqueue.size; i++)
{ {
UINT16 mapnum = roundqueue.entries[i].mapnum; mapnum = roundqueue.entries[i].mapnum;
UINT32 val = 0; // no good default, will all-but-guarantee bad save
if (mapnum < nummapheaders && mapheaderinfo[mapnum] != NULL)
val = mapheaderinfo[mapnum]->lumpnamehash;
WRITEUINT32(save->p, val); if (mapnum < nummapheaders && mapheaderinfo[mapnum] != NULL)
{
WRITEUINT8(save->p, roundqueue.entries[i].overridden);
if (roundqueue.entries[i].overridden == true)
{
WRITESTRINGL(save->p, mapheaderinfo[mapnum]->lumpname, MAXMAPLUMPNAME);
}
else
{
WRITEUINT32(save->p, mapheaderinfo[mapnum]->lumpnamehash);
}
}
else
{
// eh, not our problem. provide something that'll almost certainly fail on load
WRITEUINT8(save->p, false);
WRITEUINT32(save->p, 0);
}
} }
// Rank information // Rank information
@ -6076,15 +6092,39 @@ static boolean P_UnArchiveSPGame(savebuffer_t *save)
} }
UINT8 i, j; UINT8 i, j;
UINT16 mapnum;
for (i = 0; i < roundqueue.size; i++) for (i = 0; i < roundqueue.size; i++)
{ {
UINT32 val = READUINT32(save->p); roundqueue.entries[i].overridden = (boolean)READUINT8(save->p);
UINT16 mapnum = roundqueue.entries[i].mapnum; if (roundqueue.entries[i].overridden == true)
if (mapnum < nummapheaders && mapheaderinfo[mapnum] != NULL)
{ {
if (mapheaderinfo[mapnum]->lumpnamehash == val) if (i >= roundqueue.position)
{
CONS_Alert(CONS_ERROR, "P_UnArchiveSPGame: Cup \"%s\"'s level composition is invalid (has been overridden at entry %u/%u, ahead of the queue head %u).\n", cupname, i, roundqueue.size, roundqueue.position-1);
return false;
}
char mapname[MAXMAPLUMPNAME];
READSTRINGL(save->p, mapname, MAXMAPLUMPNAME);
mapnum = G_MapNumber(mapname);
if (mapnum < nummapheaders)
{
roundqueue.entries[i].mapnum = mapnum;
continue; continue;
}
}
else
{
UINT32 val = READUINT32(save->p);
mapnum = roundqueue.entries[i].mapnum;
if (mapnum < nummapheaders && mapheaderinfo[mapnum] != NULL)
{
if (mapheaderinfo[mapnum]->lumpnamehash == val)
continue;
}
} }
CONS_Alert(CONS_ERROR, "P_UnArchiveSPGame: Cup \"%s\"'s level composition has changed between game launches (differs at queue entry %u/%u).\n", cupname, i, roundqueue.size); CONS_Alert(CONS_ERROR, "P_UnArchiveSPGame: Cup \"%s\"'s level composition has changed between game launches (differs at queue entry %u/%u).\n", cupname, i, roundqueue.size);

View file

@ -23,7 +23,8 @@ extern "C" {
#endif #endif
// 1024 bytes is plenty for a savegame // 1024 bytes is plenty for a savegame
#define SAVEGAMESIZE (1024) // ...but we'll be accomodating of a heavily replaced Round Queue.
#define SAVEGAMESIZE (2048)
// For netgames // For netgames
#define NETSAVEGAMESIZE (768*1024) #define NETSAVEGAMESIZE (768*1024)