mirror of
https://github.com/ZDoom/gzdoom.git
synced 2025-01-31 22:00:48 +00:00
- try to keep the engine stable for as long as possible if a VM exception occurs in OnDestroy while running a cleanup.
This will still crash, but run long enough for the exception message to be visible.
This commit is contained in:
parent
936e89e3d4
commit
b6c5232fea
6 changed files with 12 additions and 11 deletions
|
@ -1069,7 +1069,7 @@ static void G_FullConsole()
|
||||||
primaryLevel->Music = "";
|
primaryLevel->Music = "";
|
||||||
S_Start();
|
S_Start();
|
||||||
S_StopMusic(true);
|
S_StopMusic(true);
|
||||||
P_FreeLevelData();
|
P_FreeLevelData(false);
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -130,7 +130,7 @@ struct FLevelLocals
|
||||||
void AddScroller(int secnum);
|
void AddScroller(int secnum);
|
||||||
void SetInterMusic(const char *nextmap);
|
void SetInterMusic(const char *nextmap);
|
||||||
void SetMusicVolume(float v);
|
void SetMusicVolume(float v);
|
||||||
void ClearLevelData();
|
void ClearLevelData(bool fullgc = true);
|
||||||
void ClearPortals();
|
void ClearPortals();
|
||||||
bool CheckIfExitIsGood(AActor *self, level_info_t *newmap);
|
bool CheckIfExitIsGood(AActor *self, level_info_t *newmap);
|
||||||
void FormatMapName(FString &mapname, const char *mapnamecolor);
|
void FormatMapName(FString &mapname, const char *mapnamecolor);
|
||||||
|
|
|
@ -279,7 +279,7 @@ void FLevelLocals::ClearPortals()
|
||||||
//
|
//
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
|
|
||||||
void FLevelLocals::ClearLevelData()
|
void FLevelLocals::ClearLevelData(bool fullgc)
|
||||||
{
|
{
|
||||||
{
|
{
|
||||||
auto it = GetThinkerIterator<AActor>(NAME_None, STAT_TRAVELLING);
|
auto it = GetThinkerIterator<AActor>(NAME_None, STAT_TRAVELLING);
|
||||||
|
@ -291,7 +291,7 @@ void FLevelLocals::ClearLevelData()
|
||||||
}
|
}
|
||||||
|
|
||||||
interpolator.ClearInterpolations(); // [RH] Nothing to interpolate on a fresh level.
|
interpolator.ClearInterpolations(); // [RH] Nothing to interpolate on a fresh level.
|
||||||
Thinkers.DestroyAllThinkers();
|
Thinkers.DestroyAllThinkers(fullgc);
|
||||||
ClearAllSubsectorLinks(); // can't be done as part of the polyobj deletion process.
|
ClearAllSubsectorLinks(); // can't be done as part of the polyobj deletion process.
|
||||||
|
|
||||||
total_monsters = total_items = total_secrets =
|
total_monsters = total_items = total_secrets =
|
||||||
|
@ -383,13 +383,13 @@ void FLevelLocals::ClearLevelData()
|
||||||
//
|
//
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
|
|
||||||
void P_FreeLevelData ()
|
void P_FreeLevelData (bool fullgc)
|
||||||
{
|
{
|
||||||
R_FreePastViewers();
|
R_FreePastViewers();
|
||||||
|
|
||||||
for (auto Level : AllLevels())
|
for (auto Level : AllLevels())
|
||||||
{
|
{
|
||||||
Level->ClearLevelData();
|
Level->ClearLevelData(fullgc);
|
||||||
}
|
}
|
||||||
// primaryLevel->FreeSecondaryLevels();
|
// primaryLevel->FreeSecondaryLevels();
|
||||||
}
|
}
|
||||||
|
|
|
@ -143,7 +143,7 @@ bool P_CheckMapData(const char * mapname);
|
||||||
void P_SetupLevel (FLevelLocals *Level, int position, bool newGame);
|
void P_SetupLevel (FLevelLocals *Level, int position, bool newGame);
|
||||||
void P_LoadLightmap(MapData *map);
|
void P_LoadLightmap(MapData *map);
|
||||||
|
|
||||||
void P_FreeLevelData();
|
void P_FreeLevelData(bool fullgc = true);
|
||||||
|
|
||||||
// Called by startup code.
|
// Called by startup code.
|
||||||
void P_Init (void);
|
void P_Init (void);
|
||||||
|
|
|
@ -271,7 +271,7 @@ void FThinkerCollection::RunThinkers(FLevelLocals *Level)
|
||||||
//
|
//
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
|
|
||||||
void FThinkerCollection::DestroyAllThinkers()
|
void FThinkerCollection::DestroyAllThinkers(bool fullgc)
|
||||||
{
|
{
|
||||||
int i;
|
int i;
|
||||||
bool error = false;
|
bool error = false;
|
||||||
|
@ -285,11 +285,12 @@ void FThinkerCollection::DestroyAllThinkers()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
error |= Thinkers[MAX_STATNUM + 1].DoDestroyThinkers();
|
error |= Thinkers[MAX_STATNUM + 1].DoDestroyThinkers();
|
||||||
GC::FullGC();
|
if (fullgc) GC::FullGC();
|
||||||
if (error)
|
if (error)
|
||||||
{
|
{
|
||||||
ClearGlobalVMStack();
|
ClearGlobalVMStack();
|
||||||
I_Error("DestroyAllThinkers failed");
|
if (fullgc) I_Error("DestroyAllThinkers failed");
|
||||||
|
else I_FatalError("DestroyAllThinkers failed");
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -79,7 +79,7 @@ struct FThinkerCollection
|
||||||
}
|
}
|
||||||
|
|
||||||
void RunThinkers(FLevelLocals *Level); // The level is needed to tick the lights
|
void RunThinkers(FLevelLocals *Level); // The level is needed to tick the lights
|
||||||
void DestroyAllThinkers();
|
void DestroyAllThinkers(bool fullgc = true);
|
||||||
void SerializeThinkers(FSerializer &arc, bool keepPlayers);
|
void SerializeThinkers(FSerializer &arc, bool keepPlayers);
|
||||||
void MarkRoots();
|
void MarkRoots();
|
||||||
DThinker *FirstThinker(int statnum);
|
DThinker *FirstThinker(int statnum);
|
||||||
|
|
Loading…
Reference in a new issue