Beispiel #1
0
 public void DisconnectConnection(long connectionId)
 {
     using (MonitorLock.CreateLock(m_disconnectionListLock))
     {
         m_disconnectionList.Add(connectionId);
     }
 }
Beispiel #2
0
        public void SendPacket(NetWrapOutgoingMessage msg, List <long> connectionIds, NetWrapOrdering delivery = NetWrapOrdering.ReliableOrdered, int sequenceChannel = 0)
        {
            if (m_valid == false)
            {
                return;
            }

            var flags = ENet.PacketFlags.None;

            if ((int)delivery >= 30)
            {
                flags |= ENet.PacketFlags.Reliable;
            }
            if (delivery == NetWrapOrdering.ReliableUnordered)
            {
                flags |= ENet.PacketFlags.Unsequenced;
            }
            msg.Flags = flags;
            foreach (var connectionId in connectionIds)
            {
                var toSendMsg = new NetWrapOutgoingMessage(msg);
                toSendMsg.ConnectionId = connectionId;
                using (MonitorLock.CreateLock(m_outgoingPacketListLocks[(m_currentOutgoingPacketListIndex + 1) % 2]))
                {
                    m_outgoingPacketLists[(m_currentOutgoingPacketListIndex + 1) % 2].Add(toSendMsg);
                }
            }
        }
Beispiel #3
0
        public void Shutdown(string p)
        {
            if (m_valid == false)
            {
                return;
            }

            if (peer.IsInitialized)
            {
                peer.DisconnectNow(p.GetHashCode());
            }
            using (MonitorLock.CreateLock(hostLock))
            {
                if (host.IsInitialized)
                {
                    m_stopThread = true;
                    m_threadStoppedEvent.WaitOne(5000);
                    try
                    {
                        host.Dispose();
                        m_valid = false;
                    }
                    catch (Exception e)
                    {
                        Console.WriteLine("Failed to shut down ENet e:" + e);
                    }
                }
            }
        }
Beispiel #4
0
 public void Flush()
 {
     using (MonitorLock.CreateLock(hostLock))
     {
         host.Flush();
     }
 }
Beispiel #5
0
        private void i_checkStartENetThread()
        {
            if (m_ENetTask == null || m_ENetTask.IsCompleted)
            {
                m_ENetTask = Task.Run(() =>
                {
                    Thread.CurrentThread.Name = "ENet Thread";
                    while (!m_stopThread || m_disconnectionList.Count != 0)
                    {
                        using (MonitorLock.CreateLock(m_outgoingPacketListLocks[m_currentOutgoingPacketListIndex]))
                        {
                            foreach (var outgoingPacket in m_outgoingPacketLists[m_currentOutgoingPacketListIndex])
                            {
                                NetWrapConnection connection;
                                if (!m_connections.TryGetValue(outgoingPacket.ConnectionId, out connection))
                                {
                                    continue;
                                }

                                if (connection.Peer.State == ENet.PeerState.Connected)
                                {
                                    connection.Peer.Send(0, outgoingPacket.Message, outgoingPacket.MessageOffset, outgoingPacket.MessageCount, outgoingPacket.Flags);
                                }
                            }
                            m_outgoingPacketLists[m_currentOutgoingPacketListIndex].Clear();
                        }

                        using (MonitorLock.CreateLock(m_disconnectionListLock))
                        {
                            foreach (var connectionId in m_disconnectionList)
                            {
                                NetWrapConnection connection;
                                if (m_connections.TryRemove(connectionId, out connection) && connection.Peer.UserData != IntPtr.Zero)
                                {
                                    GCHandle.FromIntPtr(connection.Peer.UserData).Free();
                                    connection.Peer.UserData = IntPtr.Zero;
                                }
                                if (connection.Peer.IsInitialized && connection.Peer.State == ENet.PeerState.Connected)
                                {
                                    connection.Peer.DisconnectLater("disconnect".GetHashCode());
                                }
                            }
                            m_disconnectionList.Clear();
                        }

                        using (MonitorLock.CreateLock(m_enetEventListLocks[m_currentENetEventListIndex]))
                        {
                            ENet.Event enetEvent;
                            using (MonitorLock.CreateLock(hostLock))
                            {
                                if (host.Service(0, out enetEvent))
                                {
                                    do
                                    {
                                        m_enetEventLists[m_currentENetEventListIndex].Add(enetEvent);
                                    } while (host.CheckEvents(out enetEvent));
                                }
                            }
                        }

                        Thread.Sleep(25);
                    }

                    m_threadStoppedEvent.Set();
                });
            }
        }
Beispiel #6
0
        public bool Update()
        {
            if (m_valid == false)
            {
                return(false);
            }

            i_checkStartENetThread();

            using (MonitorLock.CreateLock(m_outgoingPacketListLocks[m_currentOutgoingPacketListIndex]))
            {
                using (MonitorLock.CreateLock(m_outgoingPacketListLocks[(m_currentOutgoingPacketListIndex + 1) % 2]))
                {
                    if (m_outgoingPacketLists[(m_currentOutgoingPacketListIndex + 1) % 2].Count > 0 && m_outgoingPacketLists[m_currentOutgoingPacketListIndex].Count == 0)
                    {
                        m_currentOutgoingPacketListIndex = (m_currentOutgoingPacketListIndex + 1) % 2;
                    }
                }
            }

            using (MonitorLock.CreateLock(m_enetEventListLocks[m_currentENetEventListIndex]))
            {
                if (m_enetEventLists[m_currentENetEventListIndex].Count > 0)
                {
                    m_currentENetEventListIndex = (m_currentENetEventListIndex + 1) % 2;
                    m_enetEventLists[m_currentENetEventListIndex].Clear();
                }
            }

            using (MonitorLock.CreateLock(m_enetEventListLocks[m_currentENetEventListIndex]))
            {
                foreach (var enetEvent in m_enetEventLists[(m_currentENetEventListIndex + 1) % 2])
                {
                    if (enetEvent.Type == ENet.EventType.None)
                    {
                        continue;
                    }

                    NetWrapConnection connection;
                    if (enetEvent.Peer.UserData == IntPtr.Zero)
                    {
                        var peer = enetEvent.Peer;
                        connection = new NetWrapConnection
                        {
                            ConnectionId = connectionIDCounter++,
                            Peer         = enetEvent.Peer
                        };
                        m_connections.TryAdd(connection.ConnectionId, connection);
                        peer.UserData = GCHandle.ToIntPtr(GCHandle.Alloc(connection));
                    }
                    else
                    {
                        var gcHandle = GCHandle.FromIntPtr(enetEvent.Peer.UserData);
                        connection = (NetWrapConnection)gcHandle.Target;
                        m_connections.GetOrAdd(connection.ConnectionId, connection);
                    }

                    switch (enetEvent.Type)
                    {
                    case ENet.EventType.Connect:
                    {
                        // set timeouts
                        enetEvent.Peer.SetTimeouts(5, 30000, 90000);

                        NumConnections++;

                        var wrappedStatus = new NetWrapConnectionStatus()
                        {
                            Status       = NetWrapConnectionStatusEnum.Connected,
                            EndPoint     = enetEvent.Peer.GetRemoteAddress(),
                            ConnectionId = connection.ConnectionId
                        };
                        OnStatusChanged(this, wrappedStatus);
                    }
                    break;

                    case ENet.EventType.Disconnect:
                    {
                        NumConnections--;

                        var wrappedStatus = new NetWrapConnectionStatus()
                        {
                            Status       = NetWrapConnectionStatusEnum.Disconnected,
                            EndPoint     = enetEvent.Peer.GetRemoteAddress(),
                            ConnectionId = connection.ConnectionId
                        };
                        OnStatusChanged(this, wrappedStatus);
                    }
                    break;

                    case ENet.EventType.Receive:
                        byte[] data = enetEvent.Packet.GetBytes();
                        if (data.Length >= 5 && data[0] == RPCHeader[0] && data[1] == RPCHeader[1] && data[2] == RPCHeader[2] && data[3] == RPCHeader[3])
                        {
#if RELEASE // Needs to be #if-ed out in debug to let errors fall into the debugger
                            try
                            {
#endif
                            var rpcDataTemplate = new RPCData();
                            var msg             = new NetWrapIncomingMessage();
                            msg.SenderConnectionId          = connection.ConnectionId;
                            rpcDataTemplate.OriginalMessage = msg;

                            int offset = 5;
                            for (int i = 0; i < data[4]; i++)
                            {
                                int blockbytes = BitConverter.ToInt32(data, offset);
                                offset += 4;
                                if (blockbytes < 0)
                                {
                                    // compressed RPC call
                                    blockbytes = -blockbytes;
                                    var buffer = NetCompressByteArray.Unwrap(data, offset);
                                    var stream = new MemoryStream(buffer);
                                    RPCStream.Execute(stream, RpcDispatcher, rpcDataTemplate);
                                }
                                else
                                {
                                    // uncompressed RPC call
                                    var stream = new MemoryStream(data, offset, blockbytes);
                                    RPCStream.Execute(stream, RpcDispatcher, rpcDataTemplate);
                                }
                                offset += blockbytes;
                            }
#if RELEASE
                        }
                        catch (Exception ex)
                        {
                            try
                            {
                                using (var stream = System.IO.File.AppendText("ignored-net-errors.txt"))
                                    stream.WriteLine(DateTime.Now.ToString() + " : " + ex.ToString());
                            } catch {}

                            Console.WriteLine(ex.ToString());
                            break;
                        }
#endif
                        }
                        else
                        {
                            NetWrapIncomingMessage msg = new NetWrapIncomingMessage()
                            {
                                Message            = data,
                                MessageCount       = data.Length,
                                MessageOffset      = 0,
                                SenderConnectionId = connection.ConnectionId
                            };
                            OnData(this, msg);
                        }
                        enetEvent.Packet.Dispose();
                        break;

                    default:
                        Console.WriteLine(enetEvent.Type);
                        break;
                    }
                }
                m_enetEventLists[(m_currentENetEventListIndex + 1) % 2].Clear();
            }
            return(true);
        }