| 
									
										
										
										
											2015-02-02 01:56:53 -08:00
										 |  |  | // This file is public domain, in case it's useful to anyone. -comex
 | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | #pragma once
 | 
					
						
							|  |  |  | #include <functional>
 | 
					
						
							|  |  |  | #include <list>
 | 
					
						
							|  |  |  | #include <memory>
 | 
					
						
							| 
									
										
										
										
											2015-03-10 01:47:29 +01:00
										 |  |  | #include <random>
 | 
					
						
							| 
									
										
										
										
											2015-03-01 02:45:04 +01:00
										 |  |  | #include <enet/enet.h>
 | 
					
						
							| 
									
										
										
										
											2015-02-02 01:56:53 -08:00
										 |  |  | #include "Common/Common.h"
 | 
					
						
							|  |  |  | #include "Common/Thread.h"
 | 
					
						
							|  |  |  | #include "Common/TraversalProto.h"
 | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | class TraversalClientClient | 
					
						
							|  |  |  | { | 
					
						
							|  |  |  | public: | 
					
						
							|  |  |  | 	virtual ~TraversalClientClient(){}; | 
					
						
							|  |  |  | 	virtual void OnTraversalStateChanged()=0; | 
					
						
							|  |  |  | 	virtual void OnConnectReady(ENetAddress addr)=0; | 
					
						
							|  |  |  | 	virtual void OnConnectFailed(u8 reason)=0; | 
					
						
							|  |  |  | }; | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | class TraversalClient | 
					
						
							|  |  |  | { | 
					
						
							|  |  |  | public: | 
					
						
							|  |  |  | 	enum State | 
					
						
							|  |  |  | 	{ | 
					
						
							|  |  |  | 		Connecting, | 
					
						
							|  |  |  | 		Connected, | 
					
						
							|  |  |  | 		Failure | 
					
						
							|  |  |  | 	}; | 
					
						
							|  |  |  | 	enum FailureReason | 
					
						
							|  |  |  | 	{ | 
					
						
							|  |  |  | 		BadHost = 0x300, | 
					
						
							|  |  |  | 		VersionTooOld, | 
					
						
							|  |  |  | 		ServerForgotAboutUs, | 
					
						
							|  |  |  | 		SocketSendError, | 
					
						
							|  |  |  | 		ResendTimeout, | 
					
						
							|  |  |  | 	}; | 
					
						
							| 
									
										
										
										
											2015-02-14 19:51:08 -08:00
										 |  |  | 	TraversalClient(ENetHost* netHost, const std::string& server, const u16 port); | 
					
						
							| 
									
										
										
										
											2015-02-02 01:56:53 -08:00
										 |  |  | 	~TraversalClient(); | 
					
						
							|  |  |  | 	void Reset(); | 
					
						
							|  |  |  | 	void ConnectToClient(const std::string& host); | 
					
						
							|  |  |  | 	void ReconnectToServer(); | 
					
						
							|  |  |  | 	void Update(); | 
					
						
							|  |  |  | 	// called from NetHost
 | 
					
						
							|  |  |  | 	bool TestPacket(u8* data, size_t size, ENetAddress* from); | 
					
						
							|  |  |  | 	void HandleResends(); | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | 	ENetHost* m_NetHost; | 
					
						
							|  |  |  | 	TraversalClientClient* m_Client; | 
					
						
							|  |  |  | 	TraversalHostId m_HostId; | 
					
						
							|  |  |  | 	State m_State; | 
					
						
							|  |  |  | 	int m_FailureReason; | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | private: | 
					
						
							|  |  |  | 	struct OutgoingTraversalPacketInfo | 
					
						
							|  |  |  | 	{ | 
					
						
							|  |  |  | 		TraversalPacket packet; | 
					
						
							|  |  |  | 		int tries; | 
					
						
							|  |  |  | 		enet_uint32 sendTime; | 
					
						
							|  |  |  | 	}; | 
					
						
							|  |  |  | 	void HandleServerPacket(TraversalPacket* packet); | 
					
						
							|  |  |  | 	void ResendPacket(OutgoingTraversalPacketInfo* info); | 
					
						
							|  |  |  | 	TraversalRequestId SendTraversalPacket(const TraversalPacket& packet); | 
					
						
							| 
									
										
										
										
											2015-02-16 22:53:50 -08:00
										 |  |  | 	void OnFailure(FailureReason reason); | 
					
						
							| 
									
										
										
										
											2015-02-02 01:56:53 -08:00
										 |  |  | 	void HandlePing(); | 
					
						
							|  |  |  | 	static int ENET_CALLBACK InterceptCallback(ENetHost* host, ENetEvent* event); | 
					
						
							|  |  |  | 	TraversalRequestId m_ConnectRequestId; | 
					
						
							|  |  |  | 	bool m_PendingConnect; | 
					
						
							|  |  |  | 	std::list<OutgoingTraversalPacketInfo> m_OutgoingTraversalPackets; | 
					
						
							|  |  |  | 	ENetAddress m_ServerAddress; | 
					
						
							|  |  |  | 	std::string m_Server; | 
					
						
							| 
									
										
										
										
											2015-02-14 19:51:08 -08:00
										 |  |  | 	u16         m_port; | 
					
						
							| 
									
										
										
										
											2015-02-02 01:56:53 -08:00
										 |  |  | 	enet_uint32 m_PingTime; | 
					
						
							|  |  |  | }; | 
					
						
							|  |  |  | extern std::unique_ptr<TraversalClient> g_TraversalClient; | 
					
						
							|  |  |  | // the NetHost connected to the TraversalClient.
 | 
					
						
							|  |  |  | extern std::unique_ptr<ENetHost> g_MainNetHost; | 
					
						
							|  |  |  | // Create g_TraversalClient and g_MainNetHost if necessary.
 | 
					
						
							|  |  |  | bool EnsureTraversalClient(const std::string& server, u16 port); | 
					
						
							|  |  |  | void ReleaseTraversalClient(); |