From 193ab4905664259cbb5035b0ec9b2cb3e0e6a994 Mon Sep 17 00:00:00 2001 From: BobTheBob <32057864+BobTheBob9@users.noreply.github.com> Date: Thu, 4 Jul 2024 21:53:38 +0100 Subject: Properly handle invalid cvar replications without blocking netmessage (#408) Properly handle invalid cvar replications without blocking netmessage entirely and restore `ns_server_name` replication --- primedev/server/serverpresence.cpp | 4 +-- primedev/shared/exploit_fixes/exploitfixes.cpp | 36 +++++++++++++++++--------- 2 files changed, 26 insertions(+), 14 deletions(-) diff --git a/primedev/server/serverpresence.cpp b/primedev/server/serverpresence.cpp index 509243f0..099f6e64 100644 --- a/primedev/server/serverpresence.cpp +++ b/primedev/server/serverpresence.cpp @@ -78,7 +78,7 @@ void ServerPresenceManager::CreateConVars() Cvar_ns_server_presence_update_rate = new ConVar( "ns_server_presence_update_rate", "5000", FCVAR_GAMEDLL, "How often we update our server's presence on server lists in ms"); - Cvar_ns_server_name = new ConVar("ns_server_name", "Unnamed Northstar Server", FCVAR_GAMEDLL, "This server's name", false, 0, false, 0, [](ConVar* cvar, const char* pOldValue, float flOldValue) { + Cvar_ns_server_name = new ConVar("ns_server_name", "Unnamed Northstar Server", FCVAR_GAMEDLL | FCVAR_REPLICATED, "This server's name", false, 0, false, 0, [](ConVar* cvar, const char* pOldValue, float flOldValue) { NOTE_UNUSED(cvar); NOTE_UNUSED(pOldValue); NOTE_UNUSED(flOldValue); @@ -88,7 +88,7 @@ void ServerPresenceManager::CreateConVars() Cvar_hostname->SetValue(g_pServerPresence->Cvar_ns_server_name->GetString()); }); - Cvar_ns_server_desc = new ConVar("ns_server_desc", "Default server description", FCVAR_GAMEDLL, "This server's description", false, 0, false, 0, [](ConVar* cvar, const char* pOldValue, float flOldValue) { + Cvar_ns_server_desc = new ConVar("ns_server_desc", "Default server description", FCVAR_GAMEDLL | FCVAR_REPLICATED, "This server's description", false, 0, false, 0, [](ConVar* cvar, const char* pOldValue, float flOldValue) { NOTE_UNUSED(cvar); NOTE_UNUSED(pOldValue); NOTE_UNUSED(flOldValue); diff --git a/primedev/shared/exploit_fixes/exploitfixes.cpp b/primedev/shared/exploit_fixes/exploitfixes.cpp index d96bc41e..1b3069f5 100644 --- a/primedev/shared/exploit_fixes/exploitfixes.cpp +++ b/primedev/shared/exploit_fixes/exploitfixes.cpp @@ -120,19 +120,31 @@ bool, __fastcall, (void* pMsg)) // 48 8B D1 48 8B 49 18 48 8B 01 48 FF 60 10 if (!nameValid || !valValid) return BLOCKED_INFO("Missing null terminators"); - ConVar* pVar = g_pCVar->FindVar(entry->name); - - if (pVar) + // we only need to check if these cvars are valid on client as it will set actual cvars there + // on server this won't set any actual convars, only keyvalues in the player, which doesn't have really any potential for dumb + // stuff + if (!bIsServerFrame) { - memcpy( - entry->name, - pVar->m_ConCommandBase.m_pszName, - strlen(pVar->m_ConCommandBase.m_pszName) + 1); // Force name to match case - - int iFlags = bIsServerFrame ? FCVAR_USERINFO : FCVAR_REPLICATED; - if (!pVar->IsFlagSet(iFlags)) - return BLOCKED_INFO( - "Invalid flags (" << std::hex << "0x" << pVar->m_ConCommandBase.m_nFlags << "), var is " << entry->name); + ConVar* pVar = g_pCVar->FindVar(entry->name); + if (pVar) + { + memcpy( + entry->name, + pVar->m_ConCommandBase.m_pszName, + strlen(pVar->m_ConCommandBase.m_pszName) + 1); // Force name to match case + + if (!pVar->IsFlagSet(FCVAR_REPLICATED)) + { + spdlog::warn( + "Blocking replication of remote cvar {} from server (server's var has flag REPLICATED, while ours does not)", + entry->name); + + // don't block, as non-malicious servers might send bad cvars, and we still want those clients to be able to + // connect + memset(entry->name, 0, ENTRY_STR_LEN); + memset(entry->val, 0, ENTRY_STR_LEN); + } + } } } else -- cgit v1.2.3