From 22af41193eb8e6b84f9c2c8cca7369e329b39ee0 Mon Sep 17 00:00:00 2001 From: Ari Vuollet Date: Sun, 5 Mar 2023 18:42:16 +0200 Subject: [PATCH] Fix crash when calling RPC functions --- Source/Engine/Networking/NetworkReplicator.cs | 34 +++++++++++++++---- 1 file changed, 28 insertions(+), 6 deletions(-) diff --git a/Source/Engine/Networking/NetworkReplicator.cs b/Source/Engine/Networking/NetworkReplicator.cs index dc2bc77c8..54e0e893e 100644 --- a/Source/Engine/Networking/NetworkReplicator.cs +++ b/Source/Engine/Networking/NetworkReplicator.cs @@ -9,14 +9,23 @@ namespace FlaxEngine.Networking partial class NetworkReplicator { private static Dictionary> _managedSerializers; + private static List _managedExecuteRpcFuncs; #if FLAX_EDITOR - private static void OnScriptsReloadBegin() + private static void ClearManagedReferences() { // Clear refs to managed types that will be hot-reloaded - _managedSerializers.Clear(); - _managedSerializers = null; - FlaxEditor.ScriptsBuilder.ScriptsReloadBegin -= OnScriptsReloadBegin; + if (_managedSerializers != null) + { + _managedSerializers.Clear(); + _managedSerializers = null; + } + if (_managedExecuteRpcFuncs != null) + { + _managedExecuteRpcFuncs.Clear(); + _managedExecuteRpcFuncs = null; + } + FlaxEditor.ScriptsBuilder.ScriptsReloadBegin -= ClearManagedReferences; } #endif @@ -55,8 +64,9 @@ namespace FlaxEngine.Networking if (_managedSerializers == null) { _managedSerializers = new Dictionary>(); + _managedExecuteRpcFuncs = new List(); #if FLAX_EDITOR - FlaxEditor.ScriptsBuilder.ScriptsReloadBegin += OnScriptsReloadBegin; + FlaxEditor.ScriptsBuilder.ScriptsReloadBegin += ClearManagedReferences; #endif } _managedSerializers[type] = new KeyValuePair(serialize, deserialize); @@ -125,10 +135,22 @@ namespace FlaxEngine.Networking /// Client RPC. /// Network channel to use for RPC transport. [Unmanaged] - public static void AddRPC(Type type, string name, ExecuteRPCFunc execute, bool isServer = true, bool isClient = false, NetworkChannelType channel = NetworkChannelType.ReliableOrdered) + public static unsafe void AddRPC(Type type, string name, ExecuteRPCFunc execute, bool isServer = true, bool isClient = false, NetworkChannelType channel = NetworkChannelType.ReliableOrdered) { if (!typeof(FlaxEngine.Object).IsAssignableFrom(type)) throw new ArgumentException("Not supported type for RPC. Only FlaxEngine.Object types are valid."); + + if (_managedExecuteRpcFuncs == null) + { + _managedSerializers = new Dictionary>(); + _managedExecuteRpcFuncs = new List(); +#if FLAX_EDITOR + FlaxEditor.ScriptsBuilder.ScriptsReloadBegin += ClearManagedReferences; +#endif + } + // Store the reference to prevent garbage collection + _managedExecuteRpcFuncs.Add(execute); + Internal_AddRPC(type, name, Marshal.GetFunctionPointerForDelegate(execute), isServer, isClient, channel); } }