private void HandleRakNetMessage(IPEndPoint senderEndpoint, OpenConnectionRequest2 incoming) { PlayerNetworkSession session; lock (PlayerSessions) { DateTime trash; if (!_connectionAttemps.TryRemove(senderEndpoint, out trash)) { Log.WarnFormat("Unexpected connection request packet from {0}. Probably a resend.", senderEndpoint.Address); return; } if (PlayerSessions.TryGetValue(senderEndpoint, out session)) { // Already connecting, then this is just a duplicate if (session.State == ConnectionState.Connecting /* && DateTime.UtcNow < session.LastUpdatedTime + TimeSpan.FromSeconds(2)*/) { return; } Log.InfoFormat("Unexpected session from {0}. Removing old session and disconnecting old player.", senderEndpoint.Address); session.Disconnect("Reconnecting.", false); PlayerSessions.TryRemove(senderEndpoint, out session); } session = new PlayerNetworkSession(this, null, senderEndpoint, incoming.mtuSize) { State = ConnectionState.Connecting, LastUpdatedTime = DateTime.UtcNow, MtuSize = incoming.mtuSize, NetworkIdentifier = incoming.clientGuid }; PlayerSessions.TryAdd(senderEndpoint, session); } //Player player = PlayerFactory.CreatePlayer(this, senderEndpoint); //player.ClientGuid = incoming.clientGuid; //player.NetworkHandler = session; //session.Player = player; session.MessageHandler = new LoginMessageHandler(session); var reply = OpenConnectionReply2.CreateObject(); reply.serverGuid = 12345; reply.clientEndpoint = senderEndpoint; reply.mtuSize = incoming.mtuSize; reply.doSecurityAndHandshake = new byte[1]; var data = reply.Encode(); reply.PutPool(); TraceSend(reply); SendData(data, senderEndpoint); }
private void ProcessMessage(byte[] receiveBytes, IPEndPoint senderEndpoint) { byte msgId = receiveBytes[0]; if (msgId == 0xFE) { Log.InfoFormat("A query detected from: {0}", senderEndpoint.Address); HandleQuery(receiveBytes, senderEndpoint); } else if (msgId <= (byte)DefaultMessageIdTypes.ID_USER_PACKET_ENUM) { HandleRakNetMessage(receiveBytes, senderEndpoint, msgId); } else { PlayerNetworkSession playerSession; if (!PlayerSessions.TryGetValue(senderEndpoint, out playerSession)) { //Log.DebugFormat("Receive MCPE message 0x{1:x2} without session {0}", senderEndpoint.Address, msgId); //if (!_badPacketBans.ContainsKey(senderEndpoint.Address)) //{ // _badPacketBans.Add(senderEndpoint.Address, true); //} return; } if (playerSession.MessageHandler == null) { Log.ErrorFormat("Receive MCPE message 0x{1:x2} without message handler {0}. Session removed.", senderEndpoint.Address, msgId); PlayerSessions.TryRemove(senderEndpoint, out playerSession); //if (!_badPacketBans.ContainsKey(senderEndpoint.Address)) //{ // _badPacketBans.Add(senderEndpoint.Address, true); //} return; } if (playerSession.Evicted) { return; } playerSession.LastUpdatedTime = DateTime.UtcNow; DatagramHeader header = new DatagramHeader(receiveBytes[0]); if (!header.isACK && !header.isNAK && header.isValid) { if (receiveBytes[0] == 0xa0) { throw new Exception("Receive ERROR, NAK in wrong place"); } ConnectedPackage package = ConnectedPackage.CreateObject(); try { package.Decode(receiveBytes); } catch (Exception e) { playerSession.Disconnect("Bad package received from client."); Log.Warn($"Bad packet {receiveBytes[0]}\n{Package.HexDump(receiveBytes)}", e); GreylistManager.Blacklist(senderEndpoint.Address); return; } // IF reliable code below is enabled, useItem start sending doubles // for some unknown reason. //Reliability reliability = package._reliability; //if (reliability == Reliability.Reliable // || reliability == Reliability.ReliableSequenced // || reliability == Reliability.ReliableOrdered // ) { EnqueueAck(playerSession, package._datagramSequenceNumber); //if (Log.IsDebugEnabled) Log.Debug("ACK on #" + package._datagramSequenceNumber.IntValue()); } HandleConnectedPackage(playerSession, package); package.PutPool(); } else if (header.isACK && header.isValid) { HandleAck(playerSession, receiveBytes); } else if (header.isNAK && header.isValid) { HandleNak(playerSession, receiveBytes); } else if (!header.isValid) { Log.Warn("!!!! ERROR, Invalid header !!!!!"); } } }