mirror of
https://github.com/YGGverse/xash3d-fwgs.git
synced 2025-01-30 08:44:31 +00:00
ref: Improve model unloading, fix texture leak
This commit is contained in:
parent
3d39d78e53
commit
8339096ad8
@ -1226,7 +1226,7 @@ static qboolean CL_LoadHudSprite( const char *szSpriteName, model_t *m_pSprite,
|
|||||||
else
|
else
|
||||||
{
|
{
|
||||||
Con_Reportf( S_ERROR "Could not load HUD sprite %s\n", szSpriteName );
|
Con_Reportf( S_ERROR "Could not load HUD sprite %s\n", szSpriteName );
|
||||||
ref.dllFuncs.Mod_UnloadModel( m_pSprite );
|
Mod_FreeModel( m_pSprite );
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -1242,7 +1242,7 @@ static qboolean CL_LoadHudSprite( const char *szSpriteName, model_t *m_pSprite,
|
|||||||
|
|
||||||
if( !loaded )
|
if( !loaded )
|
||||||
{
|
{
|
||||||
ref.dllFuncs.Mod_UnloadModel( m_pSprite );
|
Mod_FreeModel( m_pSprite );
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1561,7 +1561,7 @@ void CL_RegisterResources( sizebuf_t *msg )
|
|||||||
for( i = 1, mod = clgame.sprites; i < MAX_CLIENT_SPRITES; i++, mod++ )
|
for( i = 1, mod = clgame.sprites; i < MAX_CLIENT_SPRITES; i++, mod++ )
|
||||||
{
|
{
|
||||||
if( mod->needload == NL_UNREFERENCED && COM_CheckString( mod->name ))
|
if( mod->needload == NL_UNREFERENCED && COM_CheckString( mod->name ))
|
||||||
ref.dllFuncs.Mod_UnloadModel( mod );
|
Mod_FreeModel( mod );
|
||||||
}
|
}
|
||||||
|
|
||||||
Mod_FreeUnused ();
|
Mod_FreeUnused ();
|
||||||
@ -3145,7 +3145,7 @@ void CL_LegacyPrecache_f( void )
|
|||||||
for( i = 1, mod = clgame.sprites; i < MAX_CLIENT_SPRITES; i++, mod++ )
|
for( i = 1, mod = clgame.sprites; i < MAX_CLIENT_SPRITES; i++, mod++ )
|
||||||
{
|
{
|
||||||
if( mod->needload == NL_UNREFERENCED && COM_CheckString( mod->name ))
|
if( mod->needload == NL_UNREFERENCED && COM_CheckString( mod->name ))
|
||||||
ref.dllFuncs.Mod_UnloadModel( mod );
|
Mod_FreeModel( mod );
|
||||||
}
|
}
|
||||||
|
|
||||||
// Mod_FreeUnused ();
|
// Mod_FreeUnused ();
|
||||||
|
@ -403,6 +403,7 @@ static void R_UnloadProgs( void )
|
|||||||
ref.hInstance = NULL;
|
ref.hInstance = NULL;
|
||||||
|
|
||||||
memset( &refState, 0, sizeof( refState ));
|
memset( &refState, 0, sizeof( refState ));
|
||||||
|
memset( &ref.dllFuncs, 0, sizeof( ref.dllFuncs ));
|
||||||
|
|
||||||
Cvar_Unlink( FCVAR_RENDERINFO | FCVAR_GLCONFIG );
|
Cvar_Unlink( FCVAR_RENDERINFO | FCVAR_GLCONFIG );
|
||||||
Cmd_Unlink( CMD_REFDLL );
|
Cmd_Unlink( CMD_REFDLL );
|
||||||
@ -507,10 +508,13 @@ void R_Shutdown( void )
|
|||||||
for( i = 1, mod = clgame.sprites; i < MAX_CLIENT_SPRITES; i++, mod++ )
|
for( i = 1, mod = clgame.sprites; i < MAX_CLIENT_SPRITES; i++, mod++ )
|
||||||
{
|
{
|
||||||
if( !mod->name[0] ) continue;
|
if( !mod->name[0] ) continue;
|
||||||
Mod_UnloadSpriteModel( mod );
|
Mod_FreeModel( mod );
|
||||||
}
|
}
|
||||||
memset( clgame.sprites, 0, sizeof( clgame.sprites ));
|
memset( clgame.sprites, 0, sizeof( clgame.sprites ));
|
||||||
|
|
||||||
|
// correctly free all models before render unload
|
||||||
|
// change this if need add online render changing
|
||||||
|
Mod_FreeAll();
|
||||||
R_UnloadProgs();
|
R_UnloadProgs();
|
||||||
ref.initialized = false;
|
ref.initialized = false;
|
||||||
}
|
}
|
||||||
|
@ -2797,42 +2797,6 @@ void Mod_LoadBrushModel( model_t *mod, const void *buffer, qboolean *loaded )
|
|||||||
if( loaded ) *loaded = true; // all done
|
if( loaded ) *loaded = true; // all done
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
|
||||||
=================
|
|
||||||
Mod_UnloadBrushModel
|
|
||||||
|
|
||||||
Release all uploaded textures
|
|
||||||
=================
|
|
||||||
*/
|
|
||||||
void Mod_UnloadBrushModel( model_t *mod )
|
|
||||||
{
|
|
||||||
texture_t *tx;
|
|
||||||
int i;
|
|
||||||
|
|
||||||
Assert( mod != NULL );
|
|
||||||
|
|
||||||
if( mod->type != mod_brush )
|
|
||||||
return; // not a bmodel
|
|
||||||
|
|
||||||
if( mod->name[0] != '*' )
|
|
||||||
{
|
|
||||||
#ifndef XASH_DEDICATED
|
|
||||||
for( i = 0; i < mod->numtextures; i++ )
|
|
||||||
{
|
|
||||||
tx = mod->textures[i];
|
|
||||||
if( !tx || tx->gl_texturenum == ref.dllFuncs.R_GetBuiltinTexture( REF_DEFAULT_TEXTURE ) )
|
|
||||||
continue; // free slot
|
|
||||||
|
|
||||||
ref.dllFuncs.GL_FreeTexture( tx->gl_texturenum ); // main texture
|
|
||||||
ref.dllFuncs.GL_FreeTexture( tx->fb_texturenum ); // luma texture
|
|
||||||
}
|
|
||||||
#endif
|
|
||||||
Mem_FreePool( &mod->mempool );
|
|
||||||
}
|
|
||||||
|
|
||||||
memset( mod, 0, sizeof( *mod ));
|
|
||||||
}
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
==================
|
==================
|
||||||
Mod_CheckLump
|
Mod_CheckLump
|
||||||
|
@ -118,6 +118,7 @@ extern convar_t *r_showhull;
|
|||||||
// model.c
|
// model.c
|
||||||
//
|
//
|
||||||
void Mod_Init( void );
|
void Mod_Init( void );
|
||||||
|
void Mod_FreeModel( model_t *mod );
|
||||||
void Mod_FreeAll( void );
|
void Mod_FreeAll( void );
|
||||||
void Mod_Shutdown( void );
|
void Mod_Shutdown( void );
|
||||||
void Mod_ClearUserData( void );
|
void Mod_ClearUserData( void );
|
||||||
@ -189,7 +190,6 @@ void Mod_ClearStudioCache( void );
|
|||||||
// mod_sprite.c
|
// mod_sprite.c
|
||||||
//
|
//
|
||||||
void Mod_LoadSpriteModel( model_t *mod, const void *buffer, qboolean *loaded, uint texFlags );
|
void Mod_LoadSpriteModel( model_t *mod, const void *buffer, qboolean *loaded, uint texFlags );
|
||||||
void Mod_UnloadSpriteModel( model_t *mod );
|
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#endif//MOD_LOCAL_H
|
#endif//MOD_LOCAL_H
|
||||||
|
@ -113,29 +113,3 @@ void Mod_LoadSpriteModel( model_t *mod, const void *buffer, qboolean *loaded, ui
|
|||||||
ref.dllFuncs.Mod_LoadModel( mod_sprite, mod, buffer, loaded, texFlags );
|
ref.dllFuncs.Mod_LoadModel( mod_sprite, mod, buffer, loaded, texFlags );
|
||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
|
||||||
====================
|
|
||||||
Mod_UnloadSpriteModel
|
|
||||||
|
|
||||||
release sprite model and frames
|
|
||||||
====================
|
|
||||||
*/
|
|
||||||
void Mod_UnloadSpriteModel( model_t *mod )
|
|
||||||
{
|
|
||||||
Assert( mod != NULL );
|
|
||||||
|
|
||||||
if( mod->type == mod_sprite )
|
|
||||||
{
|
|
||||||
#ifndef XASH_DEDICATED
|
|
||||||
if( host.type != HOST_DEDICATED )
|
|
||||||
{
|
|
||||||
ref.dllFuncs.Mod_UnloadModel( mod );
|
|
||||||
}
|
|
||||||
#endif
|
|
||||||
|
|
||||||
Mem_FreePool( &mod->mempool );
|
|
||||||
memset( mod, 0, sizeof( *mod ));
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
|
||||||
|
@ -1139,25 +1139,6 @@ void Mod_LoadStudioModel( model_t *mod, const void *buffer, qboolean *loaded )
|
|||||||
if( loaded ) *loaded = true;
|
if( loaded ) *loaded = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
|
||||||
=================
|
|
||||||
Mod_UnloadStudioModel
|
|
||||||
=================
|
|
||||||
*/
|
|
||||||
void Mod_UnloadStudioModel( model_t *mod )
|
|
||||||
{
|
|
||||||
Assert( mod != NULL );
|
|
||||||
|
|
||||||
if( mod->type != mod_studio )
|
|
||||||
return; // not a studio
|
|
||||||
|
|
||||||
if( Host_IsDedicated() )
|
|
||||||
ref.dllFuncs.Mod_StudioUnloadTextures( mod->cache.data );
|
|
||||||
|
|
||||||
Mem_FreePool( &mod->mempool );
|
|
||||||
memset( mod, 0, sizeof( *mod ));
|
|
||||||
}
|
|
||||||
|
|
||||||
static sv_blending_interface_t gBlendAPI =
|
static sv_blending_interface_t gBlendAPI =
|
||||||
{
|
{
|
||||||
SV_BLENDING_INTERFACE_VERSION,
|
SV_BLENDING_INTERFACE_VERSION,
|
||||||
|
@ -102,37 +102,21 @@ static void Mod_FreeUserData( model_t *mod )
|
|||||||
Mod_FreeModel
|
Mod_FreeModel
|
||||||
================
|
================
|
||||||
*/
|
*/
|
||||||
static void Mod_FreeModel( model_t *mod )
|
void Mod_FreeModel( model_t *mod )
|
||||||
{
|
{
|
||||||
// already freed?
|
// already freed?
|
||||||
if( !mod || !mod->name[0] )
|
if( !mod || !mod->name[0] )
|
||||||
return;
|
return;
|
||||||
|
|
||||||
if( mod->name[0] != '*' )
|
if( mod->type != mod_brush || mod->name[0] != '*' )
|
||||||
Mod_FreeUserData( mod );
|
|
||||||
|
|
||||||
// notify renderer about unloading
|
|
||||||
if( ref.dllFuncs.Mod_UnloadModel )
|
|
||||||
ref.dllFuncs.Mod_UnloadModel( mod );
|
|
||||||
|
|
||||||
switch( mod->type )
|
|
||||||
{
|
{
|
||||||
case mod_studio:
|
Mod_FreeUserData( mod );
|
||||||
Mod_UnloadStudioModel( mod );
|
#ifndef XASH_DEDICATED
|
||||||
break;
|
ref.dllFuncs.Mod_UnloadTextures( mod );
|
||||||
case mod_alias:
|
#endif
|
||||||
// REFTODO:
|
Mem_FreePool( &mod->mempool );
|
||||||
// Mod_UnloadAliasModel( mod );
|
|
||||||
break;
|
|
||||||
case mod_sprite:
|
|
||||||
Mod_UnloadSpriteModel( mod );
|
|
||||||
break;
|
|
||||||
case mod_brush:
|
|
||||||
Mod_UnloadBrushModel( mod );
|
|
||||||
break;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
memset( mod, 0, sizeof( *mod ));
|
memset( mod, 0, sizeof( *mod ));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -520,9 +520,8 @@ typedef struct ref_interface_s
|
|||||||
// flags ignored for everything except spritemodels
|
// flags ignored for everything except spritemodels
|
||||||
void (*Mod_LoadModel)( modtype_t desiredType, model_t *mod, const byte *buf, qboolean *loaded, int flags );
|
void (*Mod_LoadModel)( modtype_t desiredType, model_t *mod, const byte *buf, qboolean *loaded, int flags );
|
||||||
void (*Mod_LoadMapSprite)( struct model_s *mod, const void *buffer, size_t size, qboolean *loaded );
|
void (*Mod_LoadMapSprite)( struct model_s *mod, const void *buffer, size_t size, qboolean *loaded );
|
||||||
void (*Mod_UnloadModel)( model_t *mod );
|
void (*Mod_UnloadTextures)( model_t *mod );
|
||||||
void (*Mod_StudioLoadTextures)( model_t *mod, void *data );
|
void (*Mod_StudioLoadTextures)( model_t *mod, void *data );
|
||||||
void (*Mod_StudioUnloadTextures)( void *data );
|
|
||||||
|
|
||||||
// efx implementation
|
// efx implementation
|
||||||
void (*CL_DrawParticles)( double frametime, particle_t *particles, float partsize );
|
void (*CL_DrawParticles)( double frametime, particle_t *particles, float partsize );
|
||||||
|
@ -729,22 +729,12 @@ void Mod_LoadAliasModel( model_t *mod, const void *buffer, qboolean *loaded )
|
|||||||
if( loaded ) *loaded = true; // done
|
if( loaded ) *loaded = true; // done
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
void Mod_AliasUnloadTextures( void *data )
|
||||||
=================
|
|
||||||
Mod_UnloadAliasModel
|
|
||||||
=================
|
|
||||||
*/
|
|
||||||
void Mod_UnloadAliasModel( model_t *mod )
|
|
||||||
{
|
{
|
||||||
aliashdr_t *palias;
|
aliashdr_t *palias;
|
||||||
int i, j;
|
int i, j;
|
||||||
|
|
||||||
Assert( mod != NULL );
|
palias = data;
|
||||||
|
|
||||||
if( mod->type != mod_alias )
|
|
||||||
return; // not an alias
|
|
||||||
|
|
||||||
palias = mod->cache.data;
|
|
||||||
if( !palias ) return; // already freed
|
if( !palias ) return; // already freed
|
||||||
|
|
||||||
for( i = 0; i < MAX_SKINS; i++ )
|
for( i = 0; i < MAX_SKINS; i++ )
|
||||||
@ -758,9 +748,6 @@ void Mod_UnloadAliasModel( model_t *mod )
|
|||||||
GL_FreeTexture( palias->fb_texturenum[i][j] );
|
GL_FreeTexture( palias->fb_texturenum[i][j] );
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
Mem_FreePool( &mod->mempool );
|
|
||||||
memset( mod, 0, sizeof( *mod ));
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
|
@ -164,26 +164,6 @@ static void Mod_LoadModel( modtype_t desiredType, model_t *mod, const byte *buf,
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
static void Mod_UnloadModel( model_t *mod )
|
|
||||||
{
|
|
||||||
switch( mod->type )
|
|
||||||
{
|
|
||||||
case mod_studio:
|
|
||||||
// Mod_UnloadStudioModel( mod );
|
|
||||||
break;
|
|
||||||
case mod_alias:
|
|
||||||
Mod_UnloadAliasModel( mod );
|
|
||||||
break;
|
|
||||||
case mod_brush:
|
|
||||||
// Mod_UnloadBrushModel( mod );
|
|
||||||
break;
|
|
||||||
case mod_sprite:
|
|
||||||
Mod_UnloadSpriteModel( mod );
|
|
||||||
break;
|
|
||||||
default: gEngfuncs.Host_Error( "Mod_UnloadModel: unsupported type %d\n", mod->type );
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
static int GL_RenderGetParm( int parm, int arg )
|
static int GL_RenderGetParm( int parm, int arg )
|
||||||
{
|
{
|
||||||
gl_texture_t *glt;
|
gl_texture_t *glt;
|
||||||
@ -320,6 +300,45 @@ const byte *GL_TextureData( unsigned int texnum )
|
|||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void Mod_BrushUnloadTextures( model_t *mod )
|
||||||
|
{
|
||||||
|
int i;
|
||||||
|
|
||||||
|
for( i = 0; i < mod->numtextures; i++ )
|
||||||
|
{
|
||||||
|
texture_t *tx = mod->textures[i];
|
||||||
|
if( !tx || tx->gl_texturenum == tr.defaultTexture )
|
||||||
|
continue; // free slot
|
||||||
|
|
||||||
|
GL_FreeTexture( tx->gl_texturenum ); // main texture
|
||||||
|
GL_FreeTexture( tx->fb_texturenum ); // luma texture
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void Mod_UnloadTextures( model_t *mod )
|
||||||
|
{
|
||||||
|
int i, j;
|
||||||
|
|
||||||
|
Assert( mod != NULL );
|
||||||
|
|
||||||
|
switch( mod->type )
|
||||||
|
{
|
||||||
|
case mod_studio:
|
||||||
|
Mod_StudioUnloadTextures( mod->cache.data );
|
||||||
|
break;
|
||||||
|
case mod_alias:
|
||||||
|
Mod_AliasUnloadTextures( mod->cache.data );
|
||||||
|
break;
|
||||||
|
case mod_brush:
|
||||||
|
Mod_BrushUnloadTextures( mod );
|
||||||
|
break;
|
||||||
|
case mod_sprite:
|
||||||
|
Mod_SpriteUnloadTextures( mod->cache.data );
|
||||||
|
break;
|
||||||
|
default: gEngfuncs.Host_Error( "Mod_UnloadModel: unsupported type %d\n", mod->type );
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
ref_interface_t gReffuncs =
|
ref_interface_t gReffuncs =
|
||||||
{
|
{
|
||||||
R_Init,
|
R_Init,
|
||||||
@ -390,9 +409,8 @@ ref_interface_t gReffuncs =
|
|||||||
|
|
||||||
Mod_LoadModel,
|
Mod_LoadModel,
|
||||||
Mod_LoadMapSprite,
|
Mod_LoadMapSprite,
|
||||||
Mod_UnloadModel,
|
Mod_UnloadTextures,
|
||||||
Mod_StudioLoadTextures,
|
Mod_StudioLoadTextures,
|
||||||
Mod_StudioUnloadTextures,
|
|
||||||
|
|
||||||
CL_DrawParticles,
|
CL_DrawParticles,
|
||||||
CL_DrawTracers,
|
CL_DrawTracers,
|
||||||
|
@ -541,10 +541,9 @@ int R_WorldToScreen( const vec3_t point, vec3_t screen );
|
|||||||
void R_ScreenToWorld( const vec3_t screen, vec3_t point );
|
void R_ScreenToWorld( const vec3_t screen, vec3_t point );
|
||||||
qboolean R_AddEntity( struct cl_entity_s *pRefEntity, int entityType );
|
qboolean R_AddEntity( struct cl_entity_s *pRefEntity, int entityType );
|
||||||
void Mod_LoadMapSprite( struct model_s *mod, const void *buffer, size_t size, qboolean *loaded );
|
void Mod_LoadMapSprite( struct model_s *mod, const void *buffer, size_t size, qboolean *loaded );
|
||||||
void Mod_UnloadSpriteModel( struct model_s *mod );
|
void Mod_SpriteUnloadTextures( void *data );
|
||||||
void Mod_UnloadStudioModel( struct model_s *mod );
|
|
||||||
void Mod_UnloadBrushModel( struct model_s *mod );
|
|
||||||
void Mod_UnloadAliasModel( struct model_s *mod );
|
void Mod_UnloadAliasModel( struct model_s *mod );
|
||||||
|
void Mod_AliasUnloadTextures( void *data );
|
||||||
void GL_SetRenderMode( int mode );
|
void GL_SetRenderMode( int mode );
|
||||||
void R_RunViewmodelEvents( void );
|
void R_RunViewmodelEvents( void );
|
||||||
void R_DrawViewModel( void );
|
void R_DrawViewModel( void );
|
||||||
|
@ -356,14 +356,14 @@ Mod_UnloadSpriteModel
|
|||||||
release sprite model and frames
|
release sprite model and frames
|
||||||
====================
|
====================
|
||||||
*/
|
*/
|
||||||
void Mod_UnloadSpriteModel( model_t *mod )
|
void Mod_SpriteUnloadTextures( void *data )
|
||||||
{
|
{
|
||||||
msprite_t *psprite;
|
msprite_t *psprite;
|
||||||
mspritegroup_t *pspritegroup;
|
mspritegroup_t *pspritegroup;
|
||||||
mspriteframe_t *pspriteframe;
|
mspriteframe_t *pspriteframe;
|
||||||
int i, j;
|
int i, j;
|
||||||
|
|
||||||
psprite = mod->cache.data;
|
psprite = data;
|
||||||
|
|
||||||
if( psprite )
|
if( psprite )
|
||||||
{
|
{
|
||||||
|
@ -3584,7 +3584,7 @@ void Mod_StudioLoadTextures( model_t *mod, void *data )
|
|||||||
|
|
||||||
/*
|
/*
|
||||||
=================
|
=================
|
||||||
Mod_StudioLoadTextures
|
Mod_StudioUnloadTextures
|
||||||
=================
|
=================
|
||||||
*/
|
*/
|
||||||
void Mod_StudioUnloadTextures( void *data )
|
void Mod_StudioUnloadTextures( void *data )
|
||||||
|
Loading…
x
Reference in New Issue
Block a user