internal PeerConnection(TcpClient TcpConnection, PeerToPeerNetwork Network, IPEndPoint RemoteEndpoint) { this.network = Network; this.remoteEndpoint = RemoteEndpoint; this.tcpConnection = TcpConnection; this.stream = this.tcpConnection.GetStream(); }
public static void Main(string[] args) { Initialize(); try { using (PeerToPeerNetwork P2PNetwork = new PeerToPeerNetwork("Retro Peer-to-Peer example")) { P2PNetwork.OnStateChange += (sender, newstate) => Console.Out.WriteLine(newstate.ToString()); P2PNetwork.OnPeerConnected += (sender, connection) => { Console.Out.WriteLine("Client connected from: " + connection.Tcp.Client.RemoteEndPoint.ToString()); }; if (!P2PNetwork.Wait()) throw new Exception("Unable to configure Internet Gateway NAT traversal."); Console.Out.WriteLine("External IP Endpoint: " + P2PNetwork.ExternalEndpoint.ToString()); Console.Out.WriteLine("Press ENTER to try to connect."); Console.In.ReadLine(); using (PeerConnection Client = P2PNetwork.ConnectToPeer(P2PNetwork.ExternalEndpoint)) { Client.Start(); Console.In.ReadLine(); } } } catch (Exception ex) { Console.Out.WriteLine(ex.Message); Console.In.ReadLine(); } Terminate(); }
internal void UdpDatagramReceived(PeerToPeerNetwork Sender, UdpDatagramEventArgs e) { LinkedList<KeyValuePair<ushort, byte[]>> LostPackets = null; byte[] FirstPacket = null; ushort FirstPacketNr = 0; ushort PacketNr; byte[] Packet; byte[] Data = e.Data; int Len = Data.Length; int Pos = 0; int PacketLen; int Offset; byte b; lock (this.udpReceiveLock) { while (Pos < Len) { b = Data[Pos++]; PacketLen = (b & 127); Offset = 7; while (Pos < Len && (b & 128) != 0) { b = Data[Pos++]; PacketLen |= (b & 127) << Offset; Offset += 7; } if (Pos + 2 > Len) break; PacketNr = Data[Pos++]; PacketNr |= (ushort)(Data[Pos++] << 8); if (Pos + PacketLen > Len) break; Packet = new byte[PacketLen]; Array.Copy(Data, Pos, Packet, 0, PacketLen); Pos += PacketLen; if ((short)(PacketNr - this.lastReceivedPacket) > 0) { if (FirstPacket == null) { FirstPacket = Packet; FirstPacketNr = PacketNr; } else { if (LostPackets == null) LostPackets = new LinkedList<KeyValuePair<ushort, byte[]>>(); LostPackets.AddFirst(new KeyValuePair<ushort, byte[]>(PacketNr, Packet)); // Reverse order } } } if (FirstPacket != null) this.lastReceivedPacket = FirstPacketNr; } BinaryEventHandler h = this.OnReceived; if (h != null) { if (LostPackets != null) { foreach (KeyValuePair<ushort, byte[]> P in LostPackets) { try { h(this, P.Value); } catch (Exception ex) { Debug.WriteLine(ex.Message); Debug.WriteLine(ex.StackTrace.ToString()); } } } if (FirstPacket != null) { try { h(this, FirstPacket); } catch (Exception ex) { Debug.WriteLine(ex.Message); Debug.WriteLine(ex.StackTrace.ToString()); } } } }
private void p2pNetwork_OnPeerConnected(PeerToPeerNetwork Listener, PeerConnection Peer) { IPEndPoint Endpoint = (IPEndPoint)Peer.Tcp.Client.RemoteEndPoint; #if LineListener Console.Out.WriteLine("Receiving connection from " + Endpoint.ToString()); #endif lock (this.remotePlayersByEndpoint) { if (!this.remotePlayerIPs.ContainsKey(Endpoint.Address)) { Peer.Dispose(); return; } } Peer.OnClosed += new EventHandler(Peer_OnClosed); Peer.OnReceived += new BinaryEventHandler(Peer_OnReceived); BinaryOutput Output = new BinaryOutput(); Output.WriteGuid(this.localPlayer.PlayerId); Output.WriteString(this.ExternalEndpoint.Address.ToString()); Output.WriteUInt16((ushort)this.ExternalEndpoint.Port); Peer.SendTcp(Output.GetPacket()); }
private void p2pNetwork_OnUdpDatagramReceived(PeerToPeerNetwork Sender, UdpDatagramEventArgs e) { Player Player; lock (this.remotePlayersByEndpoint) { if (!this.remotePlayersByEndpoint.TryGetValue(e.RemoteEndpoint, out Player)) return; } if (Player.Connection != null) Player.Connection.UdpDatagramReceived(Sender, e); }
public MultiPlayerEnvironment(string ApplicationName, bool AllowMultipleApplicationsOnSameMachine, string MqttServer, int MqttPort, bool MqttTls, string MqttUserName, string MqttPassword, string MqttNegotiationTopic, int EstimatedMaxNrPlayers, Guid PlayerId, params KeyValuePair<string, string>[] PlayerMetaInfo) { this.localPlayer = new Player(PlayerId, new IPEndPoint(IPAddress.Any, 0), new IPEndPoint(IPAddress.Any, 0), PlayerMetaInfo); this.playersById[PlayerId] = this.localPlayer; this.applicationName = ApplicationName; this.mqttServer = MqttServer; this.mqttPort = MqttPort; this.mqttTls = MqttTls; this.mqttUserName = MqttUserName; this.mqttPassword = MqttPassword; this.mqttNegotiationTopic = MqttNegotiationTopic; this.p2pNetwork = new PeerToPeerNetwork(AllowMultipleApplicationsOnSameMachine ? this.applicationName + " (" + PlayerId.ToString() + ")" : this.applicationName, 0, EstimatedMaxNrPlayers); this.p2pNetwork.OnStateChange += this.P2PNetworkStateChange; this.p2pNetwork.OnPeerConnected += new PeerConnectedEventHandler(p2pNetwork_OnPeerConnected); this.p2pNetwork.OnUdpDatagramReceived += new UdpDatagramEvent(p2pNetwork_OnUdpDatagramReceived); }
/// <summary> /// <see cref="IDisposable.Dispose"/> /// </summary> public void Dispose() { this.CloseMqtt(); this.State = MultiPlayerState.Closed; if (this.p2pNetwork != null) { this.p2pNetwork.Dispose(); this.p2pNetwork = null; } if (this.ready != null) { this.ready.Close(); this.ready = null; } if (this.error != null) { this.error.Close(); this.error = null; } if (this.remotePlayersByEndpoint != null) { lock (this.remotePlayersByEndpoint) { this.playersById.Clear(); this.remotePlayersByIndex.Clear(); foreach (Player Player in this.remotePlayersByEndpoint.Values) { if (Player.Connection != null) Player.Connection.Dispose(); } this.remotePlayersByEndpoint.Clear(); this.remotePlayers = null; } } }