From ed1ab00fafc9ae4206848123f28ee590c755e262 Mon Sep 17 00:00:00 2001 From: Vincent Herbet Date: Wed, 3 Jun 2020 23:53:26 +0200 Subject: [PATCH] Fix internal player's team id returning -1 in a specific but valid situation (#772) * Fix internal player's team id returning -1 in a specific but valid situation * Use a local variable * Fix spaces --- amxmodx/CGameConfigs.h | 12 +++++++++++ amxmodx/emsg.cpp | 49 +++++++++++++++++++++++++++++++----------- 2 files changed, 48 insertions(+), 13 deletions(-) diff --git a/amxmodx/CGameConfigs.h b/amxmodx/CGameConfigs.h index b7d58c85..a58e6579 100644 --- a/amxmodx/CGameConfigs.h +++ b/amxmodx/CGameConfigs.h @@ -180,6 +180,18 @@ class CGameConfigManager : public IGameConfigManager member = type.fieldOffset; \ } +#define GET_OFFSET_NO_ERROR(classname, member) \ + static int member = -1; \ + if (member == -1) \ + { \ + TypeDescription type; \ + if (!CommonConfig->GetOffsetByClass(classname, #member, &type) || type.fieldOffset < 0)\ + { \ + return; \ + } \ + member = type.fieldOffset; \ + } + extern CGameConfigManager ConfigManager; extern IGameConfig *CommonConfig; diff --git a/amxmodx/emsg.cpp b/amxmodx/emsg.cpp index 9e6da0cf..6067e82f 100755 --- a/amxmodx/emsg.cpp +++ b/amxmodx/emsg.cpp @@ -88,21 +88,44 @@ void Client_TeamInfo(void* mValue) if (index < 1 || index > gpGlobals->maxClients) break; char* msg = (char*)mValue; if (!msg) break; - g_players[index].team = msg; - g_teamsIds.registerTeam(msg, -1); - g_players[index].teamId = g_teamsIds.findTeamId(msg); - /** - * CS fix for SPECTATOR team. - * - - * When a player chooses spectator, ScoreInfo is sent before TeamInfo and with 0 as index. - * This means for the first round of first spectator, SPECTATOR name is not associated with its index. - * The following fix manually sets the team index when we hit SPECTATOR team. - */ - if (g_players[index].teamId == -1 && g_bmod_cstrike && !strcmp(msg, "SPECTATOR")) + auto pPlayer = GET_PLAYER_POINTER_I(index); + + pPlayer->team = msg; + g_teamsIds.registerTeam(msg, -1); + pPlayer->teamId = g_teamsIds.findTeamId(msg); + + if (pPlayer->teamId == -1) { - g_players[index].teamId = 3; - g_teamsIds.registerTeam(msg, 3); + /** + * CS fix for SPECTATOR team. + * - + * When a player chooses spectator, ScoreInfo is sent before TeamInfo and with 0 as index. + * This means for the first round of first spectator, SPECTATOR name is not associated with its index. + * The following fix manually sets the team index when we hit SPECTATOR team. + */ + if (g_bmod_cstrike && !strcmp(msg, "SPECTATOR")) + { + pPlayer->teamId = 3; + g_teamsIds.registerTeam(msg, 3); + } + + /** + * Fixes in-between situation where the team name is not yet associated with a valid index + * and ScoreInfo is executed later (used to retrieve the index). E.g. a player is dead, + * then changes team. Index will return -1 until ScoreInfo is sent, usually at the next spawn. + */ + else if ((g_bmod_cstrike || g_bmod_dod || g_bmod_tfc || g_bmod_gearbox || g_bmod_valve) + && pPlayer->pEdict->pvPrivateData + && !pPlayer->IsAlive()) + { + GET_OFFSET_NO_ERROR("CBasePlayer", m_iTeam); + + const auto teamId = get_pdata(pPlayer->pEdict, m_iTeam); + + pPlayer->teamId = teamId; + g_teamsIds.registerTeam(msg, teamId); + } } break;