Ejemplo n.º 1
0
        //"Connect to" constructor
        internal NetPeer(NetManager netManager, IPEndPoint remoteEndPoint, byte connectNum, NetDataWriter connectData) : this(netManager, remoteEndPoint)
        {
            Initialize();
            _connectId       = DateTime.UtcNow.Ticks;
            _connectionState = ConnectionState.InProgress;
            ConnectionNum    = connectNum;

            //Make initial packet
            _connectRequestPacket = NetConnectRequestPacket.Make(connectData, _connectId);
            _connectRequestPacket.ConnectionNumber = connectNum;

            //Send request
            _netManager.SendRaw(_connectRequestPacket, _remoteEndPoint);

            NetUtils.DebugWrite(ConsoleColor.Cyan, "[CC] ConnectId: {0}, ConnectNum: {1}", _connectId, connectNum);
        }
Ejemplo n.º 2
0
        internal ConnectRequestResult ProcessConnectRequest(NetConnectRequestPacket connRequest)
        {
            //current or new request
            switch (_connectionState)
            {
            //P2P case or just ID update
            case ConnectionState.InProgress:
            case ConnectionState.Incoming:
                _connectionState = ConnectionState.Incoming;
                //change connect id if newer
                if (connRequest.ConnectionId >= _connectId)
                {
                    //Change connect id
                    _connectId    = connRequest.ConnectionId;
                    ConnectionNum = connRequest.ConnectionNumber;
                }
                return(_connectionState == ConnectionState.InProgress
                        ? ConnectRequestResult.P2PConnection
                        : ConnectRequestResult.None);

            case ConnectionState.Connected:
                //Old connect request
                if (connRequest.ConnectionId == _connectId)
                {
                    //just reply accept
                    _netManager.SendRaw(_connectAcceptPacket, _remoteEndPoint);
                }
                //New connect request
                else if (connRequest.ConnectionId > _connectId)
                {
                    return(ConnectRequestResult.Reconnection);
                }
                break;

            case ConnectionState.Disconnected:
            case ConnectionState.ShutdownRequested:
                if (connRequest.ConnectionId >= _connectId)
                {
                    return(ConnectRequestResult.NewConnection);
                }
                break;
            }
            return(ConnectRequestResult.None);
        }
Ejemplo n.º 3
0
        private void DataReceived(byte[] reusableBuffer, int count, IPEndPoint remoteEndPoint)
        {
#if STATS_ENABLED
            Statistics.PacketsReceived++;
            Statistics.BytesReceived += (uint)count;
#endif
            //Try read packet
            NetPacket packet = NetPacketPool.GetPacket(count, false);
            if (!packet.FromBytes(reusableBuffer, 0, count))
            {
                NetPacketPool.Recycle(packet);
                NetUtils.DebugWriteError("[NM] DataReceived: bad!");
                return;
            }

            //get peer
            //Check normal packets
            NetPeer netPeer;
            //old packets protection
            NetEvent netEvent;
            bool     peerFound = _peers.TryGetValue(remoteEndPoint, out netPeer);

            //Check unconnected
            switch (packet.Property)
            {
            case PacketProperty.DiscoveryRequest:
                if (!DiscoveryEnabled)
                {
                    break;
                }
                netEvent = CreateEvent(NetEventType.DiscoveryRequest);
                netEvent.RemoteEndPoint = remoteEndPoint;
                netEvent.DataReader.SetSource(packet.RawData, NetConstants.HeaderSize, count);
                EnqueueEvent(netEvent);
                break;

            case PacketProperty.DiscoveryResponse:
                netEvent = CreateEvent(NetEventType.DiscoveryResponse);
                netEvent.RemoteEndPoint = remoteEndPoint;
                netEvent.DataReader.SetSource(packet.RawData, NetConstants.HeaderSize, count);
                EnqueueEvent(netEvent);
                break;

            case PacketProperty.UnconnectedMessage:
                if (!UnconnectedMessagesEnabled)
                {
                    break;
                }

                netEvent = CreateEvent(NetEventType.ReceiveUnconnected);
                netEvent.RemoteEndPoint = remoteEndPoint;
                netEvent.DataReader.SetSource(packet.RawData, NetConstants.HeaderSize, count);
                EnqueueEvent(netEvent);
                break;

            case PacketProperty.NatIntroduction:
            case PacketProperty.NatIntroductionRequest:
            case PacketProperty.NatPunchMessage:
                if (NatPunchEnabled)
                {
                    NatPunchModule.ProcessMessage(remoteEndPoint, packet);
                }
                break;

            case PacketProperty.Disconnect:
                if (peerFound)
                {
                    var disconnectResult = netPeer.ProcessDisconnect(packet);
                    if (disconnectResult == DisconnectResult.None)
                    {
                        NetPacketPool.Recycle(packet);
                        return;
                    }
                    if (disconnectResult == DisconnectResult.Disconnect)
                    {
                        _connectedPeersCount--;
                    }
                    netEvent      = CreateEvent(NetEventType.Disconnect);
                    netEvent.Peer = netPeer;
                    netEvent.DataReader.SetSource(packet.RawData, 9, packet.Size);
                    netEvent.DisconnectReason = disconnectResult == DisconnectResult.Disconnect
                            ? DisconnectReason.RemoteConnectionClose
                            : DisconnectReason.ConnectionRejected;
                    EnqueueEvent(netEvent);
                }
                else
                {
                    NetPacketPool.Recycle(packet);
                }
                //Send shutdown
                SendRaw(new[] { (byte)PacketProperty.ShutdownOk }, 0, 1, remoteEndPoint);
                break;

            case PacketProperty.ConnectAccept:
                var connAccept = NetConnectAcceptPacket.FromData(packet);
                if (connAccept != null && peerFound && netPeer.ProcessConnectAccept(connAccept))
                {
                    var connectEvent = CreateEvent(NetEventType.Connect);
                    connectEvent.Peer = netPeer;
                    EnqueueEvent(connectEvent);
                }
                break;

            case PacketProperty.ConnectRequest:
                var connRequest = NetConnectRequestPacket.FromData(packet);
                if (connRequest != null)
                {
                    ProcessConnectRequest(remoteEndPoint, netPeer, connRequest);
                }
                break;

            default:
                if (peerFound)
                {
                    netPeer.ProcessPacket(packet);
                }
                break;
            }
        }
Ejemplo n.º 4
0
        private void ProcessConnectRequest(
            IPEndPoint remoteEndPoint,
            NetPeer netPeer,
            NetConnectRequestPacket connRequest)
        {
            byte     connectionNumber = connRequest.ConnectionNumber;
            NetEvent netEvent;

            NetUtils.DebugWrite("ConnectRequest LastId: {0}, NewId: {1}, EP: {2}", netPeer.ConnectId, connRequest.ConnectionId, remoteEndPoint);

            //if we have peer
            if (netPeer != null)
            {
                var processResult = netPeer.ProcessConnectRequest(connRequest);
                switch (processResult)
                {
                case ConnectRequestResult.Reconnection:
                    _connectedPeersCount--;
                    netEvent                  = CreateEvent(NetEventType.Disconnect);
                    netEvent.Peer             = netPeer;
                    netEvent.DisconnectReason = DisconnectReason.RemoteConnectionClose;
                    EnqueueEvent(netEvent);
                    _peers.RemovePeer(netPeer);
                    //go to new connection
                    break;

                case ConnectRequestResult.NewConnection:
                    _peers.RemovePeer(netPeer);
                    //go to new connection
                    break;

                case ConnectRequestResult.P2PConnection:
                    netEvent = CreateEvent(NetEventType.ConnectionRequest);
                    netEvent.ConnectionRequest = new ConnectionRequest(
                        netPeer.ConnectId,
                        connectionNumber,
                        ConnectionRequestType.PeerToPeer,
                        connRequest.Data,
                        netPeer,
                        OnConnectionSolved);
                    EnqueueEvent(netEvent);
                    return;

                default:
                    //no operations needed
                    return;
                }
                //ConnectRequestResult.NewConnection
                //Set next connection number
                connectionNumber = (byte)((netPeer.ConnectionNum + 1) % NetConstants.MaxConnectionNumber);
                //To reconnect peer
            }
            //Add new peer and craete ConnectRequest event
            NetUtils.DebugWrite("[NM] Creating request event: " + connRequest.ConnectionId);
            netPeer = new NetPeer(this, remoteEndPoint);
            if (_peers.TryAdd(netPeer))
            {
                netEvent = CreateEvent(NetEventType.ConnectionRequest);
                netEvent.ConnectionRequest = new ConnectionRequest(
                    connRequest.ConnectionId,
                    connectionNumber,
                    ConnectionRequestType.Incoming,
                    connRequest.Data,
                    netPeer,
                    OnConnectionSolved);
                EnqueueEvent(netEvent);
            }
        }