internal static void Send(ulong clientId, byte messageType, string channelName, BitStream messageStream, SecuritySendFlags flags, NetworkedObject targetObject) { messageStream.PadStream(); if (NetworkingManager.Singleton.IsServer && clientId == NetworkingManager.Singleton.ServerClientId) { return; } if (targetObject != null && !targetObject.observers.Contains(clientId)) { if (NetworkLog.CurrentLogLevel <= LogLevel.Developer) { NetworkLog.LogWarning("Silently suppressed send call because it was directed to an object without visibility"); } return; } using (BitStream stream = MessagePacker.WrapMessage(messageType, clientId, messageStream, flags)) { NetworkProfiler.StartEvent(TickType.Send, (uint)stream.Length, channelName, MLAPIConstants.MESSAGE_NAMES[messageType]); NetworkingManager.Singleton.NetworkConfig.NetworkTransport.Send(clientId, new ArraySegment <byte>(stream.GetBuffer(), 0, (int)stream.Length), channelName); NetworkProfiler.EndEvent(); } }
internal static void Send(byte messageType, NetworkChannel networkChannel, ulong clientIdToIgnore, NetworkBuffer messageBuffer) { messageBuffer.PadBuffer(); using (var buffer = MessagePacker.WrapMessage(messageType, messageBuffer)) { #if !UNITY_2020_2_OR_NEWER NetworkProfiler.StartEvent(TickType.Send, (uint)buffer.Length, networkChannel, NetworkConstants.MESSAGE_NAMES[messageType]); #endif for (int i = 0; i < NetworkManager.Singleton.ConnectedClientsList.Count; i++) { if (NetworkManager.Singleton.ConnectedClientsList[i].ClientId == clientIdToIgnore || (NetworkManager.Singleton.IsServer && NetworkManager.Singleton.ConnectedClientsList[i].ClientId == NetworkManager.Singleton.ServerClientId)) { continue; } NetworkManager.Singleton.NetworkConfig.NetworkTransport.Send(NetworkManager.Singleton.ConnectedClientsList[i].ClientId, new ArraySegment <byte>(buffer.GetBuffer(), 0, (int)buffer.Length), networkChannel); ProfilerStatManager.BytesSent.Record((int)buffer.Length); PerformanceDataManager.Increment(ProfilerConstants.ByteSent, (int)buffer.Length); } #if !UNITY_2020_2_OR_NEWER NetworkProfiler.EndEvent(); #endif } }
//Slightly slower because of all the safety checks with the list but convenient static public void SendToSpecific(List <ulong> clientIDs, byte messageType, byte channel, BitStream messageStream) { if (clientIDs == null) { Debug.LogError("Client ID list is null."); return; } if (clientIDs.Count == 0) { return; //No one to send to. } messageStream.PadStream(); using (BitStream stream = MessagePacker.WrapMessage(messageType, 0, messageStream, SecuritySendFlags.None)) { for (int i = 0; i < clientIDs.Count; i++) { if (NetworkManager.Get().isServer&& clientIDs[i] == NetworkManager.Get().serverID) { continue; } NetworkManager.Get().transport.Send(clientIDs[i], new ArraySegment <byte>(stream.GetBuffer(), 0, (int)stream.Length), channel); } } }
/// <summary> /// Hides an object from all clients. /// Server only. /// </summary> public void NetworkHideAll() { //A faster message send bypassing MessageSender completely using (PooledBitStream baseStream = PooledBitStream.Get()) { DoVisibleHideWrite(baseStream); baseStream.PadStream(); using (BitStream stream = MessagePacker.WrapMessage(networkBehaviourManager.unspawnMessageType, 0, baseStream, SecuritySendFlags.None)) { using (List <ulong> .Enumerator clients = networkManager.clients) { while (clients.MoveNext()) { if (clients.Current == networkManager.serverID) { continue; } if (!m_PendingObservers.Remove(clients.Current) && !m_Observers.Remove(clients.Current)) { continue; } networkManager.transport.Send(clients.Current, new ArraySegment <byte>(stream.GetBuffer(), 0, (int)stream.Length), networkManager.networkInternalChannel); } } } } }
/// <summary> /// Removes all ownership of an object from any client and returns ownership to the server. Can only be called by the server or the owner of this Network Behaviour. /// </summary> public void RemoveOwnership() { if (!networkManager.isRunning) { Debug.LogError("Cannot remove ownership. The network is not running."); return; } if (!isNetworkSpawned) { throw new NetworkException("Cannot change ownership. This Network Behaviour is not spawned."); } if (!isServer && !isOwner) { throw new NotServerException("Only the server can call NetworkBehaviour.RemoveOwnership when they are not the owner of the Network Behaviour."); } //Owner does not change if (isOwnedByServer) { return; } if (isServer) { m_OwnerClientID = networkManager.serverID; OnGainedOwnership(); } using (PooledBitStream baseStream = PooledBitStream.Get()) { DoOwnershipWrite(baseStream, networkManager.serverID); if (isServer) { baseStream.PadStream(); using (BitStream stream = MessagePacker.WrapMessage(networkBehaviourManager.ownerChangeMessageType, 0, baseStream, SecuritySendFlags.None)) { using (HashSet <ulong> .Enumerator observers = GetObservers()) { while (observers.MoveNext()) { if (observers.Current == NetworkManager.Get().serverID) { continue; } NetworkManager.Get().transport.Send(observers.Current, new ArraySegment <byte>(stream.GetBuffer(), 0, (int)stream.Length), networkManager.networkInternalChannel); } } } } else { MessageSender.Send(networkManager.serverID, networkBehaviourManager.ownerChangeMessageType, networkManager.networkInternalChannel, baseStream); } } }
internal void Send(byte messageType, NetworkChannel networkChannel, List <ulong> clientIds, NetworkBuffer messageBuffer) { if (clientIds == null) { Send(messageType, networkChannel, messageBuffer); return; } messageBuffer.PadBuffer(); using (var buffer = MessagePacker.WrapMessage(messageType, messageBuffer)) { #if !UNITY_2020_2_OR_NEWER NetworkProfiler.StartEvent(TickType.Send, (uint)buffer.Length, networkChannel, NetworkConstants.MESSAGE_NAMES[messageType]); #endif for (int i = 0; i < clientIds.Count; i++) { if (m_NetworkManager.IsServer && clientIds[i] == m_NetworkManager.ServerClientId) { continue; } m_NetworkManager.NetworkConfig.NetworkTransport.Send(clientIds[i], new ArraySegment <byte>(buffer.GetBuffer(), 0, (int)buffer.Length), networkChannel); ProfilerStatManager.BytesSent.Record((int)buffer.Length); PerformanceDataManager.Increment(ProfilerConstants.ByteSent, (int)buffer.Length); } #if !UNITY_2020_2_OR_NEWER NetworkProfiler.EndEvent(); #endif } }
static public void Send(ulong clientID, byte messageType, byte channel, BitStream messageStream) { messageStream.PadStream(); if (NetworkManager.Get().isServer&& clientID == NetworkManager.Get().serverID) { return; } using (BitStream stream = MessagePacker.WrapMessage(messageType, clientID, messageStream, SecuritySendFlags.None)) { NetworkManager.Get().transport.Send(clientID, new ArraySegment <byte>(stream.GetBuffer(), 0, (int)stream.Length), channel); } }
internal static void Send(byte messageType, string channelName, ulong clientIdToIgnore, BitStream messageStream, SecuritySendFlags flags, NetworkedObject targetObject) { bool encrypted = ((flags & SecuritySendFlags.Encrypted) == SecuritySendFlags.Encrypted) && NetworkingManager.Singleton.NetworkConfig.EnableEncryption; bool authenticated = ((flags & SecuritySendFlags.Authenticated) == SecuritySendFlags.Authenticated) && NetworkingManager.Singleton.NetworkConfig.EnableEncryption; if (encrypted || authenticated) { for (int i = 0; i < NetworkingManager.Singleton.ConnectedClientsList.Count; i++) { if (NetworkingManager.Singleton.ConnectedClientsList[i].ClientId == clientIdToIgnore) { continue; } Send(NetworkingManager.Singleton.ConnectedClientsList[i].ClientId, messageType, channelName, messageStream, flags, targetObject); } } else { messageStream.PadStream(); using (BitStream stream = MessagePacker.WrapMessage(messageType, 0, messageStream, flags)) { NetworkProfiler.StartEvent(TickType.Send, (uint)stream.Length, channelName, MLAPIConstants.MESSAGE_NAMES[messageType]); for (int i = 0; i < NetworkingManager.Singleton.ConnectedClientsList.Count; i++) { if (NetworkingManager.Singleton.ConnectedClientsList[i].ClientId == clientIdToIgnore || (NetworkingManager.Singleton.IsServer && NetworkingManager.Singleton.ConnectedClientsList[i].ClientId == NetworkingManager.Singleton.ServerClientId)) { continue; } if (targetObject != null && !targetObject.observers.Contains(NetworkingManager.Singleton.ConnectedClientsList[i].ClientId)) { if (NetworkLog.CurrentLogLevel <= LogLevel.Developer) { NetworkLog.LogWarning("Silently suppressed send(ignore) call because it was directed to an object without visibility"); } continue; } NetworkingManager.Singleton.NetworkConfig.NetworkTransport.Send(NetworkingManager.Singleton.ConnectedClientsList[i].ClientId, new ArraySegment <byte>(stream.GetBuffer(), 0, (int)stream.Length), channelName); } NetworkProfiler.EndEvent(); } } }
/// <summary> /// Does not supress errors invloving clients that already have visibility of this Network Behaviour. /// Server only. /// </summary> /// <param name="clientIDs"></param> public void NetworkShow(List <ulong> clientIDs, Stream spawnPayload = null) { //A faster message send bypassing MessageSender completely if (clientIDs == null) { throw new ArgumentNullException(nameof(clientIDs)); } using (PooledBitStream baseStream = PooledBitStream.Get()) { DoVisibleShowWrite(baseStream, spawnPayload); baseStream.PadStream(); if (clientIDs.Count == 0) { return; //No one to send to. } using (BitStream stream = MessagePacker.WrapMessage(networkBehaviourManager.spawnMessageType, 0, baseStream, SecuritySendFlags.None)) { for (int i = 0; i < clientIDs.Count; i++) { if (clientIDs[i] == NetworkManager.Get().serverID) { continue; } if (m_PendingObservers.Contains(clientIDs[i])) { Debug.LogError("This Network Behaviour is already pending visibility to client '" + clientIDs[i] + "'. Watch for a call to NetworkStart for when it successfully connects.", this); continue; } if (m_Observers.Contains(clientIDs[i])) { Debug.LogError("This Network Behaviour is already pending visibility to client '" + clientIDs[i] + "'. Watch for a call to NetworkStart for when it successfully connects.", this); continue; } m_PendingObservers.Add(clientIDs[i]); NetworkManager.Get().transport.Send(clientIDs[i], new ArraySegment <byte>(stream.GetBuffer(), 0, (int)stream.Length), networkManager.networkInternalChannel); } } } }
static public void SendToAll(byte messageType, byte channel, BitStream messageStream) { messageStream.PadStream(); using (BitStream stream = MessagePacker.WrapMessage(messageType, 0, messageStream, SecuritySendFlags.None)) { using (List <ulong> .Enumerator clients = NetworkManager.Get().clients) { while (clients.MoveNext()) { if (NetworkManager.Get().isServer&& clients.Current == NetworkManager.Get().serverID) { continue; } NetworkManager.Get().transport.Send(clients.Current, new ArraySegment <byte>(stream.GetBuffer(), 0, (int)stream.Length), channel); } } } }
internal static void Send(ulong clientId, byte messageType, NetworkChannel networkChannel, NetworkBuffer messageBuffer) { messageBuffer.PadBuffer(); if (NetworkManager.Singleton.IsServer && clientId == NetworkManager.Singleton.ServerClientId) { return; } using (var buffer = MessagePacker.WrapMessage(messageType, messageBuffer)) { NetworkProfiler.StartEvent(TickType.Send, (uint)buffer.Length, networkChannel, NetworkConstants.MESSAGE_NAMES[messageType]); NetworkManager.Singleton.NetworkConfig.NetworkTransport.Send(clientId, new ArraySegment <byte>(buffer.GetBuffer(), 0, (int)buffer.Length), networkChannel); ProfilerStatManager.BytesSent.Record((int)buffer.Length); PerformanceDataManager.Increment(ProfilerConstants.ByteSent, (int)buffer.Length); #if !UNITY_2020_2_OR_NEWER NetworkProfiler.EndEvent(); #endif } }
/// <summary> /// Hides an object from a specific clients. /// Server only. /// </summary> /// <param name="clientIDs">The clients to hide the object from.</param> public void NetworkHide(List <ulong> clientIDs) { //A faster message send bypassing MessageSender completely if (clientIDs == null) { throw new ArgumentNullException(nameof(clientIDs)); } using (PooledBitStream baseStream = PooledBitStream.Get()) { DoVisibleHideWrite(baseStream); baseStream.PadStream(); if (clientIDs.Count == 0) { return; //No one to send to. } using (BitStream stream = MessagePacker.WrapMessage(networkBehaviourManager.unspawnMessageType, 0, baseStream, SecuritySendFlags.None)) { for (int i = 0; i < clientIDs.Count; i++) { if (clientIDs[i] == networkManager.serverID) { continue; } if (!m_PendingObservers.Remove(clientIDs[i]) && !m_Observers.Remove(clientIDs[i])) { Debug.LogError("This Network Behaviour is already not visible to client '" + clientIDs[i] + "'.", this); continue; } networkManager.transport.Send(clientIDs[i], new ArraySegment <byte>(stream.GetBuffer(), 0, (int)stream.Length), networkManager.networkInternalChannel); } } } }
public void MessageHandlerReceivedMessageServerClient() { // Init var gameObject = new GameObject(nameof(MessageHandlerReceivedMessageServerClient)); var networkManager = gameObject.AddComponent <NetworkManager>(); var transport = gameObject.AddComponent <DummyTransport>(); // MLAPI sets this in validate networkManager.NetworkConfig = new NetworkConfig() { // Set the current scene to prevent unexpected log messages which would trigger a failure RegisteredScenes = new List <string>() { SceneManager.GetActiveScene().name } }; // Set dummy transport that does nothing networkManager.NetworkConfig.NetworkTransport = transport; // Replace the real message handler with a dummy one that just prints a result networkManager.MessageHandler = new DummyMessageHandler(); using (var inputBuffer = new NetworkBuffer()) { // Start server since pre-message-handler passes IsServer & IsClient checks networkManager.StartServer(); // Disable batching to make the RPCs come straight through // This has to be done post start networkManager.RpcQueueContainer.EnableBatchedRpcs(false); // Should cause log (server only) LogAssert.Expect(LogType.Log, nameof(MessageHandlerReceivedMessageServerClient) + " " + nameof(DummyMessageHandler.HandleConnectionRequest)); using (var messageStream = MessagePacker.WrapMessage(NetworkConstants.CONNECTION_REQUEST, inputBuffer)) { networkManager.HandleIncomingData(0, NetworkChannel.Internal, new ArraySegment <byte>(messageStream.GetBuffer(), 0, (int)messageStream.Length), 0, true); } // Should not cause log (client only) using (var messageStream = MessagePacker.WrapMessage(NetworkConstants.CONNECTION_APPROVED, inputBuffer)) { networkManager.HandleIncomingData(0, NetworkChannel.Internal, new ArraySegment <byte>(messageStream.GetBuffer(), 0, (int)messageStream.Length), 0, true); } // Should not cause log (client only) using (var messageStream = MessagePacker.WrapMessage(NetworkConstants.ADD_OBJECT, inputBuffer)) { networkManager.HandleIncomingData(0, NetworkChannel.Internal, new ArraySegment <byte>(messageStream.GetBuffer(), 0, (int)messageStream.Length), 0, true); } // Should not cause log (client only) using (var messageStream = MessagePacker.WrapMessage(NetworkConstants.DESTROY_OBJECT, inputBuffer)) { networkManager.HandleIncomingData(0, NetworkChannel.Internal, new ArraySegment <byte>(messageStream.GetBuffer(), 0, (int)messageStream.Length), 0, true); } // Should not cause log (client only) using (var messageStream = MessagePacker.WrapMessage(NetworkConstants.SWITCH_SCENE, inputBuffer)) { networkManager.HandleIncomingData(0, NetworkChannel.Internal, new ArraySegment <byte>(messageStream.GetBuffer(), 0, (int)messageStream.Length), 0, true); } // Should not cause log (client only) using (var messageStream = MessagePacker.WrapMessage(NetworkConstants.CHANGE_OWNER, inputBuffer)) { networkManager.HandleIncomingData(0, NetworkChannel.Internal, new ArraySegment <byte>(messageStream.GetBuffer(), 0, (int)messageStream.Length), 0, true); } // Should not cause log (client only) using (var messageStream = MessagePacker.WrapMessage(NetworkConstants.ADD_OBJECTS, inputBuffer)) { networkManager.HandleIncomingData(0, NetworkChannel.Internal, new ArraySegment <byte>(messageStream.GetBuffer(), 0, (int)messageStream.Length), 0, true); } // Should not cause log (client only) using (var messageStream = MessagePacker.WrapMessage(NetworkConstants.DESTROY_OBJECTS, inputBuffer)) { networkManager.HandleIncomingData(0, NetworkChannel.Internal, new ArraySegment <byte>(messageStream.GetBuffer(), 0, (int)messageStream.Length), 0, true); } // Should not cause log (client only) using (var messageStream = MessagePacker.WrapMessage(NetworkConstants.TIME_SYNC, inputBuffer)) { networkManager.HandleIncomingData(0, NetworkChannel.Internal, new ArraySegment <byte>(messageStream.GetBuffer(), 0, (int)messageStream.Length), 0, true); } // Should cause log (server and client) LogAssert.Expect(LogType.Log, nameof(MessageHandlerReceivedMessageServerClient) + " " + nameof(DummyMessageHandler.HandleNetworkVariableDelta)); using (var messageStream = MessagePacker.WrapMessage(NetworkConstants.NETWORK_VARIABLE_DELTA, inputBuffer)) { networkManager.HandleIncomingData(0, NetworkChannel.Internal, new ArraySegment <byte>(messageStream.GetBuffer(), 0, (int)messageStream.Length), 0, true); } // Should cause log (server and client) LogAssert.Expect(LogType.Log, nameof(MessageHandlerReceivedMessageServerClient) + " " + nameof(DummyMessageHandler.HandleNetworkVariableUpdate)); using (var messageStream = MessagePacker.WrapMessage(NetworkConstants.NETWORK_VARIABLE_UPDATE, inputBuffer)) { networkManager.HandleIncomingData(0, NetworkChannel.Internal, new ArraySegment <byte>(messageStream.GetBuffer(), 0, (int)messageStream.Length), 0, true); } // Should cause log (server and client) LogAssert.Expect(LogType.Log, nameof(MessageHandlerReceivedMessageServerClient) + " " + nameof(DummyMessageHandler.HandleUnnamedMessage)); using (var messageStream = MessagePacker.WrapMessage(NetworkConstants.UNNAMED_MESSAGE, inputBuffer)) { networkManager.HandleIncomingData(0, NetworkChannel.Internal, new ArraySegment <byte>(messageStream.GetBuffer(), 0, (int)messageStream.Length), 0, true); } // Should cause log (server and client) LogAssert.Expect(LogType.Log, nameof(MessageHandlerReceivedMessageServerClient) + " " + nameof(DummyMessageHandler.HandleNamedMessage)); using (var messageStream = MessagePacker.WrapMessage(NetworkConstants.NAMED_MESSAGE, inputBuffer)) { networkManager.HandleIncomingData(0, NetworkChannel.Internal, new ArraySegment <byte>(messageStream.GetBuffer(), 0, (int)messageStream.Length), 0, true); } // Should cause log (server only) LogAssert.Expect(LogType.Log, nameof(MessageHandlerReceivedMessageServerClient) + " " + nameof(DummyMessageHandler.HandleClientSwitchSceneCompleted)); using (var messageStream = MessagePacker.WrapMessage(NetworkConstants.CLIENT_SWITCH_SCENE_COMPLETED, inputBuffer)) { networkManager.HandleIncomingData(0, NetworkChannel.Internal, new ArraySegment <byte>(messageStream.GetBuffer(), 0, (int)messageStream.Length), 0, true); } // Should cause log (server only) LogAssert.Expect(LogType.Log, nameof(MessageHandlerReceivedMessageServerClient) + " " + nameof(DummyMessageHandler.HandleNetworkLog)); using (var messageStream = MessagePacker.WrapMessage(NetworkConstants.SERVER_LOG, inputBuffer)) { networkManager.HandleIncomingData(0, NetworkChannel.Internal, new ArraySegment <byte>(messageStream.GetBuffer(), 0, (int)messageStream.Length), 0, true); } // Should cause log (server only) LogAssert.Expect(LogType.Log, nameof(MessageHandlerReceivedMessageServerClient) + " " + nameof(DummyMessageHandler.RpcReceiveQueueItem)); using (var messageStream = MessagePacker.WrapMessage(NetworkConstants.SERVER_RPC, inputBuffer)) { networkManager.HandleIncomingData(0, NetworkChannel.Internal, new ArraySegment <byte>(messageStream.GetBuffer(), 0, (int)messageStream.Length), 0, true); } // Should not cause log (client only) using (var messageStream = MessagePacker.WrapMessage(NetworkConstants.CLIENT_RPC, inputBuffer)) { networkManager.HandleIncomingData(0, NetworkChannel.Internal, new ArraySegment <byte>(messageStream.GetBuffer(), 0, (int)messageStream.Length), 0, true); } // Stop server to trigger full shutdown networkManager.StopServer(); // Replace the real message handler with a dummy one that just prints a result networkManager.MessageHandler = new DummyMessageHandler(); // Start client since pre-message-handler passes IsServer & IsClient checks networkManager.StartClient(); // Disable batching to make the RPCs come straight through // This has to be done post start (and post restart since the queue container is reset) networkManager.RpcQueueContainer.EnableBatchedRpcs(false); // Should not cause log (server only) using (var messageStream = MessagePacker.WrapMessage(NetworkConstants.CONNECTION_REQUEST, inputBuffer)) { networkManager.HandleIncomingData(0, NetworkChannel.Internal, new ArraySegment <byte>(messageStream.GetBuffer(), 0, (int)messageStream.Length), 0, true); } // Should cause log (client only) LogAssert.Expect(LogType.Log, nameof(MessageHandlerReceivedMessageServerClient) + " " + nameof(DummyMessageHandler.HandleConnectionApproved)); using (var messageStream = MessagePacker.WrapMessage(NetworkConstants.CONNECTION_APPROVED, inputBuffer)) { networkManager.HandleIncomingData(0, NetworkChannel.Internal, new ArraySegment <byte>(messageStream.GetBuffer(), 0, (int)messageStream.Length), 0, true); } // Should cause log (client only) LogAssert.Expect(LogType.Log, nameof(MessageHandlerReceivedMessageServerClient) + " " + nameof(DummyMessageHandler.HandleAddObject)); using (var messageStream = MessagePacker.WrapMessage(NetworkConstants.ADD_OBJECT, inputBuffer)) { networkManager.HandleIncomingData(0, NetworkChannel.Internal, new ArraySegment <byte>(messageStream.GetBuffer(), 0, (int)messageStream.Length), 0, true); } // Should cause log (client only) LogAssert.Expect(LogType.Log, nameof(MessageHandlerReceivedMessageServerClient) + " " + nameof(DummyMessageHandler.HandleDestroyObject)); using (var messageStream = MessagePacker.WrapMessage(NetworkConstants.DESTROY_OBJECT, inputBuffer)) { networkManager.HandleIncomingData(0, NetworkChannel.Internal, new ArraySegment <byte>(messageStream.GetBuffer(), 0, (int)messageStream.Length), 0, true); } // Should cause log (client only) LogAssert.Expect(LogType.Log, nameof(MessageHandlerReceivedMessageServerClient) + " " + nameof(DummyMessageHandler.HandleSwitchScene)); using (var messageStream = MessagePacker.WrapMessage(NetworkConstants.SWITCH_SCENE, inputBuffer)) { networkManager.HandleIncomingData(0, NetworkChannel.Internal, new ArraySegment <byte>(messageStream.GetBuffer(), 0, (int)messageStream.Length), 0, true); } // Should cause log (client only) LogAssert.Expect(LogType.Log, nameof(MessageHandlerReceivedMessageServerClient) + " " + nameof(DummyMessageHandler.HandleChangeOwner)); using (var messageStream = MessagePacker.WrapMessage(NetworkConstants.CHANGE_OWNER, inputBuffer)) { networkManager.HandleIncomingData(0, NetworkChannel.Internal, new ArraySegment <byte>(messageStream.GetBuffer(), 0, (int)messageStream.Length), 0, true); } // Should cause log (client only) LogAssert.Expect(LogType.Log, nameof(MessageHandlerReceivedMessageServerClient) + " " + nameof(DummyMessageHandler.HandleAddObjects)); using (var messageStream = MessagePacker.WrapMessage(NetworkConstants.ADD_OBJECTS, inputBuffer)) { networkManager.HandleIncomingData(0, NetworkChannel.Internal, new ArraySegment <byte>(messageStream.GetBuffer(), 0, (int)messageStream.Length), 0, true); } // Should cause log (client only) LogAssert.Expect(LogType.Log, nameof(MessageHandlerReceivedMessageServerClient) + " " + nameof(DummyMessageHandler.HandleDestroyObjects)); using (var messageStream = MessagePacker.WrapMessage(NetworkConstants.DESTROY_OBJECTS, inputBuffer)) { networkManager.HandleIncomingData(0, NetworkChannel.Internal, new ArraySegment <byte>(messageStream.GetBuffer(), 0, (int)messageStream.Length), 0, true); } // Should cause log (client only) LogAssert.Expect(LogType.Log, nameof(MessageHandlerReceivedMessageServerClient) + " " + nameof(DummyMessageHandler.HandleTimeSync)); using (var messageStream = MessagePacker.WrapMessage(NetworkConstants.TIME_SYNC, inputBuffer)) { networkManager.HandleIncomingData(0, NetworkChannel.Internal, new ArraySegment <byte>(messageStream.GetBuffer(), 0, (int)messageStream.Length), 0, true); } // Should cause log (server and client) LogAssert.Expect(LogType.Log, nameof(MessageHandlerReceivedMessageServerClient) + " " + nameof(DummyMessageHandler.HandleNetworkVariableDelta)); using (var messageStream = MessagePacker.WrapMessage(NetworkConstants.NETWORK_VARIABLE_DELTA, inputBuffer)) { networkManager.HandleIncomingData(0, NetworkChannel.Internal, new ArraySegment <byte>(messageStream.GetBuffer(), 0, (int)messageStream.Length), 0, true); } // Should cause log (server and client) LogAssert.Expect(LogType.Log, nameof(MessageHandlerReceivedMessageServerClient) + " " + nameof(DummyMessageHandler.HandleNetworkVariableUpdate)); using (var messageStream = MessagePacker.WrapMessage(NetworkConstants.NETWORK_VARIABLE_UPDATE, inputBuffer)) { networkManager.HandleIncomingData(0, NetworkChannel.Internal, new ArraySegment <byte>(messageStream.GetBuffer(), 0, (int)messageStream.Length), 0, true); } // Should cause log (server and client) LogAssert.Expect(LogType.Log, nameof(MessageHandlerReceivedMessageServerClient) + " " + nameof(DummyMessageHandler.HandleUnnamedMessage)); using (var messageStream = MessagePacker.WrapMessage(NetworkConstants.UNNAMED_MESSAGE, inputBuffer)) { networkManager.HandleIncomingData(0, NetworkChannel.Internal, new ArraySegment <byte>(messageStream.GetBuffer(), 0, (int)messageStream.Length), 0, true); } // Should cause log (server and client) LogAssert.Expect(LogType.Log, nameof(MessageHandlerReceivedMessageServerClient) + " " + nameof(DummyMessageHandler.HandleNamedMessage)); using (var messageStream = MessagePacker.WrapMessage(NetworkConstants.NAMED_MESSAGE, inputBuffer)) { networkManager.HandleIncomingData(0, NetworkChannel.Internal, new ArraySegment <byte>(messageStream.GetBuffer(), 0, (int)messageStream.Length), 0, true); } // Should not cause log (server only) using (var messageStream = MessagePacker.WrapMessage(NetworkConstants.CLIENT_SWITCH_SCENE_COMPLETED, inputBuffer)) { networkManager.HandleIncomingData(0, NetworkChannel.Internal, new ArraySegment <byte>(messageStream.GetBuffer(), 0, (int)messageStream.Length), 0, true); } // Should not cause log (server only) using (var messageStream = MessagePacker.WrapMessage(NetworkConstants.SERVER_LOG, inputBuffer)) { networkManager.HandleIncomingData(0, NetworkChannel.Internal, new ArraySegment <byte>(messageStream.GetBuffer(), 0, (int)messageStream.Length), 0, true); } // Should not cause log (server only) using (var messageStream = MessagePacker.WrapMessage(NetworkConstants.SERVER_RPC, inputBuffer)) { networkManager.HandleIncomingData(0, NetworkChannel.Internal, new ArraySegment <byte>(messageStream.GetBuffer(), 0, (int)messageStream.Length), 0, true); } // Should cause log (client only) LogAssert.Expect(LogType.Log, nameof(MessageHandlerReceivedMessageServerClient) + " " + nameof(DummyMessageHandler.RpcReceiveQueueItem)); using (var messageStream = MessagePacker.WrapMessage(NetworkConstants.CLIENT_RPC, inputBuffer)) { networkManager.HandleIncomingData(0, NetworkChannel.Internal, new ArraySegment <byte>(messageStream.GetBuffer(), 0, (int)messageStream.Length), 0, true); } // Full cleanup networkManager.StopClient(); } // Ensure no missmatches with expectations LogAssert.NoUnexpectedReceived(); // Cleanup Object.DestroyImmediate(gameObject); }
/// <summary> /// Changes the owner of the object. Can only be called from the server or the owner of this Network Behaviour. /// </summary> /// <param name="targetClientID">The new owner clientId</param> public void SetOwner(ulong targetClientID) { if (!networkManager.isRunning) { Debug.LogError("Cannot set ownership. The network is not running."); return; } if (!isServer) { if (isOwner && targetClientID == networkManager.serverID) { RemoveOwnership(); return; } throw new NotServerException("Only the server can call NetworkBehaviour.SetOwner to target anything but the server."); } if (!isNetworkSpawned) { throw new NetworkException("Cannot change ownership. This Network Behaviour is not spawned."); } if (!IsNetworkVisibleTo(targetClientID)) { throw new NetworkException("Cannot change ownership to a client that does not have visibility of this Network Behaviour."); } //Owner does not change if (targetClientID == ownerID) { return; } if (targetClientID == networkManager.serverID) { RemoveOwnership(); return; } if (isOwner) { m_OwnerClientID = targetClientID; OnLostOwnership(); } else //This may seem redundant but we want ownership changes to be set before the OnLostOwnership call { m_OwnerClientID = targetClientID; } //Send to all (not pending)observers using (PooledBitStream baseStream = PooledBitStream.Get()) { DoOwnershipWrite(baseStream, targetClientID); baseStream.PadStream(); using (BitStream stream = MessagePacker.WrapMessage(networkBehaviourManager.ownerChangeMessageType, 0, baseStream, SecuritySendFlags.None)) { using (HashSet <ulong> .Enumerator observers = GetObservers()) { while (observers.MoveNext()) { if (observers.Current == NetworkManager.Get().serverID) { continue; } NetworkManager.Get().transport.Send(observers.Current, new ArraySegment <byte>(stream.GetBuffer(), 0, (int)stream.Length), networkManager.networkInternalChannel); } } } } }