From 52aa63979389a54bcf1e1da16f57022686390a56 Mon Sep 17 00:00:00 2001 From: "seer-by-sentry[bot]" <157164994+seer-by-sentry[bot]@users.noreply.github.com> Date: Thu, 7 May 2026 21:22:10 +0000 Subject: [PATCH] bugfix(network): Prevent crash during Steam Networking Sockets re-initialization --- .../GameNetwork/GeneralsOnline/NetworkMesh.cpp | 13 +++++++++++++ 1 file changed, 13 insertions(+) diff --git a/GeneralsMD/Code/GameEngine/Source/GameNetwork/GeneralsOnline/NetworkMesh.cpp b/GeneralsMD/Code/GameEngine/Source/GameNetwork/GeneralsOnline/NetworkMesh.cpp index e6fa595230a..959a463ec16 100644 --- a/GeneralsMD/Code/GameEngine/Source/GameNetwork/GeneralsOnline/NetworkMesh.cpp +++ b/GeneralsMD/Code/GameEngine/Source/GameNetwork/GeneralsOnline/NetworkMesh.cpp @@ -566,6 +566,15 @@ NetworkMesh::NetworkMesh() { SteamNetworkingUtils()->SetGlobalConfigValueInt32(k_ESteamNetworkingConfig_LogLevel_P2PRendezvous, k_ESteamNetworkingSocketsDebugOutputType_Error); + // Block the status-changed callback from firing while the library is + // torn down and re-initialized. Without this guard the callback can + // be dispatched (e.g. from a previous Tick's RunCallbacks queue) after + // GameNetworkingSockets_Kill() has freed its internal mutexes but + // before GameNetworkingSockets_Init() has rebuilt them, resulting in + // an EXCEPTION_ACCESS_VIOLATION_READ on a null mutex pointer inside + // mtx_do_lock. + g_bNetworkMeshDestroying.store(true); + // try a shutdown GameNetworkingSockets_Kill(); @@ -658,6 +667,10 @@ NetworkMesh::NetworkMesh() SteamNetworkingUtils()->SetGlobalCallback_SteamNetConnectionStatusChanged(OnSteamNetConnectionStatusChanged); + // Library is fully re-initialized and the callback is registered; + // it is now safe to allow OnSteamNetConnectionStatusChanged to run. + g_bNetworkMeshDestroying.store(false); + ESteamNetworkingSocketsDebugOutputType logType = #if defined(_DEBUG) ESteamNetworkingSocketsDebugOutputType::k_ESteamNetworkingSocketsDebugOutputType_Debug