Skip to content

Commit

Permalink
Fix scene file loading memory errors
Browse files Browse the repository at this point in the history
Fixes leaks.
Also safeguards against deallocated pointers by doing
g_TokenProcessor.SetBuffer(NULL) after parsing is done - an access at
NULL should be easier to debug than at some random address, potentially
just reading in garbage data.
  • Loading branch information
z33ky committed Jul 2, 2021
1 parent e989cf6 commit b41d49c
Showing 1 changed file with 22 additions and 9 deletions.
31 changes: 22 additions & 9 deletions sp/src/game/server/sceneentity.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -3735,7 +3735,7 @@ CChoreoScene *CSceneEntity::LoadScene( const char *filename, IChoreoEventCallbac
Q_FixSlashes( loadfile );

// binary compiled vcd
void *pBuffer;
void *pBuffer = NULL;
#ifdef MAPBASE
//
// Raw scene file support
Expand All @@ -3760,12 +3760,13 @@ CChoreoScene *CSceneEntity::LoadScene( const char *filename, IChoreoEventCallbac
{
g_TokenProcessor.SetBuffer((char*)pBuffer);
pScene = ChoreoLoadScene( loadfile, NULL, &g_TokenProcessor, LocalScene_Printf );
g_TokenProcessor.SetBuffer(NULL);
}
// Okay, it's definitely missing.
else
{
MissingSceneWarning( loadfile );
return NULL;
pScene = NULL;
}

if (pScene)
Expand Down Expand Up @@ -4283,6 +4284,7 @@ CBaseEntity *CSceneEntity::FindNamedEntity( const char *name, CBaseEntity *pActo
#ifdef MAPBASE
const char *GetFirstSoundInScene(const char *pszScene)
{
const char *soundName;
SceneCachedData_t sceneData;
if ( scenefilecache->GetSceneCachedData( pszScene, &sceneData ) )
{
Expand All @@ -4292,7 +4294,7 @@ const char *GetFirstSoundInScene(const char *pszScene)
short stringId = scenefilecache->GetSceneCachedSound( sceneData.sceneId, 0 );

// Trust that it's been precached
return scenefilecache->GetSceneString( stringId );
soundName = scenefilecache->GetSceneString( stringId );
}
}
else
Expand All @@ -4302,20 +4304,25 @@ const char *GetFirstSoundInScene(const char *pszScene)
{
g_TokenProcessor.SetBuffer((char*)pBuffer);
CChoreoScene *pScene = ChoreoLoadScene( pszScene, NULL, &g_TokenProcessor, LocalScene_Printf );
g_TokenProcessor.SetBuffer(NULL);
if (pScene)
{
for (int i = 0; i < pScene->GetNumEvents(); i++)
{
CChoreoEvent *pEvent = pScene->GetEvent(i);

if (pEvent->GetType() == CChoreoEvent::SPEAK)
return pEvent->GetParameters();
{
soundName = pEvent->GetParameters();
break;
}
}
}
}
FreeSceneFileMemory( pBuffer );
}

return NULL;
return soundName;
}

const char *GetFirstSoundInScene(CChoreoScene *scene)
Expand Down Expand Up @@ -4483,6 +4490,8 @@ bool CSceneEntity::ScriptLoadSceneFromString(const char* pszFilename, const char
PrecacheScene(pScene);
}

g_TokenProcessor.SetBuffer(NULL);

if (pScene != NULL)
{
// release prior scene if present
Expand Down Expand Up @@ -5284,12 +5293,12 @@ int GetSceneSpeechCount( char const *pszScene )
else
{
void *pBuffer = NULL;
int iNumSounds = 0;
if (filesystem->ReadFileEx( pszScene, "MOD", &pBuffer, true ))
{
int iNumSounds = 0;

g_TokenProcessor.SetBuffer((char*)pBuffer);
CChoreoScene *pScene = ChoreoLoadScene( pszScene, NULL, &g_TokenProcessor, LocalScene_Printf );
g_TokenProcessor.SetBuffer(NULL);
if (pScene)
{
for (int i = 0; i < pScene->GetNumEvents(); i++)
Expand All @@ -5300,9 +5309,11 @@ int GetSceneSpeechCount( char const *pszScene )
iNumSounds++;
}
}

return iNumSounds;
}

FreeSceneFileMemory( pBuffer );

return iNumSounds;
}
#endif
return 0;
Expand Down Expand Up @@ -5367,7 +5378,9 @@ void PrecacheInstancedScene( char const *pszScene )
{
PrecacheChoreoScene(pScene);
}
g_TokenProcessor.SetBuffer(NULL);
}
FreeSceneFileMemory( pBuffer );
#else
// Scenes are sloppy and don't always exist.
// A scene that is not in the pre-built cache image, but on disk, is a true error.
Expand Down

0 comments on commit b41d49c

Please sign in to comment.