From 224e9238db7a4821ef04105f953b4122ae38fb53 Mon Sep 17 00:00:00 2001 From: Joonas Rikkonen Date: Mon, 29 Oct 2018 20:37:25 +0200 Subject: [PATCH] EntityEvents are written and sent even if the entity has been removed at the time of writing. Otherwise the clients may not receive some important events, e.g. when an item applies a statuseffect to something or triggers an explosion and is removed immediately afterwards. I'm not 100% confident that this won't cause any additional issues, so it still needs more testing. See #839 --- .../NetEntityEvent/ClientEntityEventManager.cs | 11 +++++++++++ Barotrauma/BarotraumaShared/Source/Map/Hull.cs | 2 +- .../NetEntityEvent/NetEntityEventManager.cs | 8 +++----- .../NetEntityEvent/ServerEntityEventManager.cs | 11 +++++++++++ 4 files changed, 26 insertions(+), 6 deletions(-) diff --git a/Barotrauma/BarotraumaClient/Source/Networking/NetEntityEvent/ClientEntityEventManager.cs b/Barotrauma/BarotraumaClient/Source/Networking/NetEntityEvent/ClientEntityEventManager.cs index 2cc539440..3b76c9c44 100644 --- a/Barotrauma/BarotraumaClient/Source/Networking/NetEntityEvent/ClientEntityEventManager.cs +++ b/Barotrauma/BarotraumaClient/Source/Networking/NetEntityEvent/ClientEntityEventManager.cs @@ -46,6 +46,17 @@ namespace Barotrauma.Networking return; } + if (((Entity)entity).Removed) + { + DebugConsole.ThrowError("Can't create an entity event for " + entity + " - the entity has been removed.\n" + Environment.StackTrace); + return; + } + if (((Entity)entity).IdFreed) + { + DebugConsole.ThrowError("Can't create an entity event for " + entity + " - the ID of the entity has been freed.\n" + Environment.StackTrace); + return; + } + ID++; var newEvent = new ClientEntityEvent(entity, ID); newEvent.CharacterStateID = GameMain.Client.Character.LastNetworkUpdateID; diff --git a/Barotrauma/BarotraumaShared/Source/Map/Hull.cs b/Barotrauma/BarotraumaShared/Source/Map/Hull.cs index 4f2fb775f..fb8a5b7fd 100644 --- a/Barotrauma/BarotraumaShared/Source/Map/Hull.cs +++ b/Barotrauma/BarotraumaShared/Source/Map/Hull.cs @@ -387,7 +387,7 @@ namespace Barotrauma { fireSources.Add(fireSource); - if (GameMain.Server != null) GameMain.Server.CreateEntityEvent(this); + if (GameMain.Server != null && !IdFreed) GameMain.Server.CreateEntityEvent(this); } public override void Update(float deltaTime, Camera cam) diff --git a/Barotrauma/BarotraumaShared/Source/Networking/NetEntityEvent/NetEntityEventManager.cs b/Barotrauma/BarotraumaShared/Source/Networking/NetEntityEvent/NetEntityEventManager.cs index 5c1d1d2c7..69aea9ae2 100644 --- a/Barotrauma/BarotraumaShared/Source/Networking/NetEntityEvent/NetEntityEventManager.cs +++ b/Barotrauma/BarotraumaShared/Source/Networking/NetEntityEvent/NetEntityEventManager.cs @@ -56,22 +56,20 @@ namespace Barotrauma.Networking GameAnalyticsSDK.Net.EGAErrorSeverity.Error, "Too much data in network event for entity \"" + e.Entity.ToString() + "\" (" + tempEventBuffer.LengthBytes + " bytes"); - //write an empty event breaking the event syncing + //write an empty event to prevent breaking the event syncing tempBuffer.Write((UInt16)0); tempBuffer.WritePadBits(); eventCount++; continue; - } - //the ID has been taken by another entity (the original entity has been removed) -> write an empty event - else if (Entity.FindEntityByID(e.Entity.ID) != e.Entity || e.Entity.IdFreed) + /*else if (Entity.FindEntityByID(e.Entity.ID) != e.Entity || e.Entity.IdFreed) { //technically the clients don't have any use for these, but removing events and shifting the IDs of all //consecutive ones is so error-prone that I think this is a safer option tempBuffer.Write((UInt16)0); tempBuffer.WritePadBits(); - } + }*/ else { tempBuffer.Write((UInt16)e.Entity.ID); diff --git a/Barotrauma/BarotraumaShared/Source/Networking/NetEntityEvent/ServerEntityEventManager.cs b/Barotrauma/BarotraumaShared/Source/Networking/NetEntityEvent/ServerEntityEventManager.cs index 69413017a..543da0c9c 100644 --- a/Barotrauma/BarotraumaShared/Source/Networking/NetEntityEvent/ServerEntityEventManager.cs +++ b/Barotrauma/BarotraumaShared/Source/Networking/NetEntityEvent/ServerEntityEventManager.cs @@ -75,6 +75,17 @@ namespace Barotrauma.Networking return; } + if (((Entity)entity).Removed) + { + DebugConsole.ThrowError("Can't create an entity event for " + entity + " - the entity has been removed.\n"+Environment.StackTrace); + return; + } + if (((Entity)entity).IdFreed) + { + DebugConsole.ThrowError("Can't create an entity event for " + entity + " - the ID of the entity has been freed.\n"+Environment.StackTrace); + return; + } + var newEvent = new ServerEntityEvent(entity, (UInt16)(ID + 1)); if (extraData != null) newEvent.SetData(extraData);