Browse Source

engine: server: make PEntityOfEntIndex bug-compatible with GoldSrc

Add new undocumented GoldSrc eiface function, PEntityOfEntIndexAllEntities,
a bug-free version of PEntityOfEntIndex

Ref: https://github.com/ValveSoftware/halflife/issues/2272
pull/2/head
Alibek Omarov 3 years ago committed by a1batross
parent
commit
51526948c0
  1. 1
      engine/common/common.h
  2. 3
      engine/eiface.h
  3. 1
      engine/server/server.h
  4. 49
      engine/server/sv_game.c

1
engine/common/common.h

@ -756,7 +756,6 @@ void pfnDrawSetTextColor( float r, float g, float b ); @@ -756,7 +756,6 @@ void pfnDrawSetTextColor( float r, float g, float b );
void pfnDrawConsoleStringLen( const char *pText, int *length, int *height );
void *Cache_Check( poolhandle_t mempool, struct cache_user_s *c );
void COM_TrimSpace( const char *source, char *dest );
edict_t* pfnPEntityOfEntIndex( int iEntIndex );
void pfnGetModelBounds( model_t *mod, float *mins, float *maxs );
void pfnCVarDirectSet( cvar_t *var, const char *szValue );
int COM_CheckParm( char *parm, char **ppnext );

3
engine/eiface.h

@ -278,6 +278,9 @@ typedef struct enginefuncs_s @@ -278,6 +278,9 @@ typedef struct enginefuncs_s
void (*pfnQueryClientCvarValue)( const edict_t *player, const char *cvarName );
void (*pfnQueryClientCvarValue2)( const edict_t *player, const char *cvarName, int requestID );
int (*pfnCheckParm)( char *parm, char **ppnext );
// added in 8279
edict_t* (*pfnPEntityOfEntIndexAllEntities)( int iEntIndex );
} enginefuncs_t;
// ONLY ADD NEW FUNCTIONS TO THE END OF THIS STRUCT. INTERFACE VERSION IS FROZEN AT 138

1
engine/server/server.h

@ -628,7 +628,6 @@ void SV_StartSound( edict_t *ent, int chan, const char *sample, float vol, float @@ -628,7 +628,6 @@ void SV_StartSound( edict_t *ent, int chan, const char *sample, float vol, float
edict_t *SV_FindGlobalEntity( string_t classname, string_t globalname );
qboolean SV_CreateStaticEntity( struct sizebuf_s *msg, int index );
void SV_SendUserReg( sizebuf_t *msg, sv_user_message_t *user );
edict_t* pfnPEntityOfEntIndex( int iEntIndex );
int pfnIndexOfEdict( const edict_t *pEdict );
void pfnWriteBytes( const byte *bytes, int count );
void SV_UpdateBaseVelocity( edict_t *ent );

49
engine/server/sv_game.c

@ -60,6 +60,21 @@ qboolean SV_CheckEdict( const edict_t *e, const char *file, const int line ) @@ -60,6 +60,21 @@ qboolean SV_CheckEdict( const edict_t *e, const char *file, const int line )
}
#endif
static edict_t *SV_PEntityOfEntIndex( const int iEntIndex, const qboolean allentities )
{
edict_t *pEdict = EDICT_NUM( iEntIndex );
qboolean player = allentities ? iEntIndex <= svs.maxclients : iEntIndex < svs.maxclients;
if( !SV_IsValidEdict( pEdict ))
return NULL;
if( !player && !pEdict->pvPrivateData )
return NULL;
return pEdict;
}
/*
=============
EntvarsDescription
@ -586,7 +601,7 @@ void SV_RestartAmbientSounds( void ) @@ -586,7 +601,7 @@ void SV_RestartAmbientSounds( void )
continue;
S_StopSound( si->entnum, si->channel, si->name );
SV_StartSound( pfnPEntityOfEntIndex( si->entnum ), CHAN_STATIC, si->name, si->volume, si->attenuation, 0, si->pitch );
SV_StartSound( SV_PEntityOfEntIndex( si->entnum, true ), CHAN_STATIC, si->name, si->volume, si->attenuation, 0, si->pitch );
}
#if !XASH_DEDICATED // TODO: ???
@ -640,10 +655,10 @@ void SV_RestartDecals( void ) @@ -640,10 +655,10 @@ void SV_RestartDecals( void )
for( i = 0; i < host.numdecals; i++ )
{
entry = &host.decalList[i];
modelIndex = pfnPEntityOfEntIndex( entry->entityIndex )->v.modelindex;
modelIndex = SV_PEntityOfEntIndex( entry->entityIndex, true )->v.modelindex;
// game override
if( SV_RestoreCustomDecal( entry, pfnPEntityOfEntIndex( entry->entityIndex ), false ))
if( SV_RestoreCustomDecal( entry, SV_PEntityOfEntIndex( entry->entityIndex, true ), false ))
continue;
decalIndex = pfnDecalIndex( entry->name );
@ -3350,24 +3365,21 @@ pfnPEntityOfEntIndex @@ -3350,24 +3365,21 @@ pfnPEntityOfEntIndex
=============
*/
edict_t *pfnPEntityOfEntIndex( int iEntIndex )
static edict_t *pfnPEntityOfEntIndex( int iEntIndex )
{
if( iEntIndex >= 0 && iEntIndex < GI->max_edicts )
{
edict_t *pEdict = EDICT_NUM( iEntIndex );
if( !iEntIndex || FBitSet( host.features, ENGINE_QUAKE_COMPATIBLE ))
return pEdict; // just get access to array
if( SV_IsValidEdict( pEdict ) && pEdict->pvPrivateData )
return pEdict;
// have to be bug-compatible with GoldSrc in this function
return SV_PEntityOfEntIndex( iEntIndex, false );
}
// g-cont: world and clients can be acessed even without private data!
if( SV_IsValidEdict( pEdict ) && SV_IsPlayerIndex( iEntIndex ))
return pEdict;
}
/*
=============
pfnPEntityOfEntIndexAllEntities
return NULL;
=============
*/
static edict_t *pfnPEntityOfEntIndexAllEntities( int iEntIndex )
{
return SV_PEntityOfEntIndex( iEntIndex, true );
}
/*
@ -4740,6 +4752,7 @@ static enginefuncs_t gEngfuncs = @@ -4740,6 +4752,7 @@ static enginefuncs_t gEngfuncs =
pfnQueryClientCvarValue,
pfnQueryClientCvarValue2,
COM_CheckParm,
pfnPEntityOfEntIndexAllEntities,
};
/*

Loading…
Cancel
Save