1 /// \file
2 /// \brief Declares RakPeer class.
3 ///
4 /// This file is part of RakNet Copyright 2003 Jenkins Software LLC
5 ///
6 /// Raknet is available under the terms of the GPLv3 license, see /usr/local/share/licenses/raknet-3.9.2_10,1/GPLv3.
7 
8 
9 #ifndef __RAK_PEER_H
10 #define __RAK_PEER_H
11 
12 #include "ReliabilityLayer.h"
13 #include "RakPeerInterface.h"
14 #include "RPCNode.h"
15 #include "RSACrypt.h"
16 #include "BitStream.h"
17 #include "SingleProducerConsumer.h"
18 #include "RPCMap.h"
19 #include "SimpleMutex.h"
20 #include "DS_OrderedList.h"
21 #include "Export.h"
22 #include "RakString.h"
23 #include "RakThread.h"
24 #include "RakNetSocket.h"
25 #include "RakNetSmartPtr.h"
26 #include "DS_ThreadsafeAllocatingQueue.h"
27 #include "SignaledEvent.h"
28 
29 class HuffmanEncodingTree;
30 class PluginInterface2;
31 
32 // Sucks but this struct has to be outside the class.  Inside and DevCPP won't let you refer to the struct as RakPeer::RemoteSystemIndex while GCC
33 // forces you to do RakPeer::RemoteSystemIndex
34 struct RemoteSystemIndex{unsigned index; RemoteSystemIndex *next;};
35 //int RAK_DLL_EXPORT SystemAddressAndIndexComp( const SystemAddress &key, const RemoteSystemIndex &data ); // GCC requires RakPeer::RemoteSystemIndex or it won't compile
36 
37 // TODO - RakNet 4 Move plugins to each sample directory respectively, to reduce the lib size
38 
39 ///\brief Main interface for network communications.
40 /// \details It implements most of RakNet's functionality and is the primary interface for RakNet.
41 ///
42 /// Inherits RakPeerInterface.
43 ///
44 /// See the individual functions for what the class can do.
45 ///
46 class RAK_DLL_EXPORT RakPeer : public RakPeerInterface
47 {
48 public:
49 	///Constructor
50 	RakPeer();
51 
52 	///Destructor
53 	virtual ~RakPeer();
54 
55 	// --------------------------------------------------------------------------------------------Major Low Level Functions - Functions needed by most users--------------------------------------------------------------------------------------------
56 	/// \brief Starts the network threads and opens the listen port.
57 	/// \details You must call this before calling Connect().
58 	/// \note Multiple calls while already active are ignored.  To call this function again with different settings, you must first call Shutdown().
59 	/// \note Call SetMaximumIncomingConnections if you want to accept incoming connections.
60 	/// \note Set _RAKNET_THREADSAFE in RakNetDefines.h if you want to call RakNet functions from multiple threads (not recommended, as it is much slower and RakNet is already asynchronous).
61 	/// \param[in] maxConnections Maximum number of connections between this instance of RakPeer and another instance of RakPeer. Required so that the network can preallocate and for thread safety. A pure client would set this to 1.  A pure server would set it to the number of allowed clients.A hybrid would set it to the sum of both types of connections.
62 	/// \param[in] localPort Port to listen for connections on.
63 	/// \param[in] _threadSleepTimer Time in milliseconds for the thread to Sleep in each internal update cycle. With new congestion control, the best results will be obtained by passing 10.
64 	/// \param[in] socketDescriptors An array of SocketDescriptor structures to force RakNet to listen on a particular IP address or port (or both).  Each SocketDescriptor will represent one unique socket.  Do not pass redundant structures.  To listen on a specific port, you can pass SocketDescriptor(myPort,0); for a server.  For a client, it is usually OK to pass SocketDescriptor();
65 	/// \param[in] socketDescriptorCount The size of the \a socketDescriptors array.  Pass 1 if you are not sure what to pass.
66 	/// \param[in] threadPriority Passed to the thread creation routine. Use THREAD_PRIORITY_NORMAL for Windows. For Linux based systems, you MUST pass something reasonable based on the thread priorities for your application.
67 	/// \return False on failure (can't create socket or thread), true on success.
68 	bool Startup( unsigned short maxConnections, int _threadSleepTimer, SocketDescriptor *socketDescriptors, unsigned socketDescriptorCount, int threadPriority=-99999 );
69 
70 	/// \brief Secures connections though a combination of SHA1, AES128, SYN Cookies, and RSA to prevent connection spoofing, replay attacks, data eavesdropping, packet tampering, and MitM attacks.
71 	/// \details If you accept connections, you must call this for the secure connection to be enabled for incoming connections.
72 	/// If you are connecting to another system, you can call this with public key values for p,q and e before connecting to prevent MitM.
73 	/// Define how many bits are used in RakNetDefines.h with RAKNET_RSA_FACTOR_LIMBS.
74 	/// \note There is a significant amount of processing and a slight amount of bandwidth overhead for this feature.
75 	/// \pre Must be called before Initialize.
76 	/// \param[in] pubKeyE A pointer to the public keys from the RSACrypt class.
77 	/// \param[in] pubKeyN A pointer to the public keys from the RSACrypt class.
78 	/// \param[in] privKeyP Public key generated from the RSACrypt class.
79 	/// \param[in] privKeyQ Public key generated from the RSACrypt class.  If the private keys are 0, then a new key will be generated when this function is called@see the Encryption sample
80 	void InitializeSecurity(const char *pubKeyE, const char *pubKeyN, const char *privKeyP, const char *privKeyQ );
81 
82 	/// \brief Disables all security.
83 	/// \note Must be called while offline.
84 	void DisableSecurity( void );
85 
86 	/// \brief This is useful if you have a fixed-address internal server behind a LAN.
87 	///
88 	///  Secure connections are determined by the recipient of an incoming connection. This has no effect if called on the system attempting to connect.
89 	/// \note If secure connections are on, do not use secure connections for a specific IP address.
90 	/// \param[in] ip IP address to add. * wildcards are supported.
91 	void AddToSecurityExceptionList(const char *ip);
92 
93 	/// \brief Remove a specific connection previously added via AddToSecurityExceptionList.
94 	/// \param[in] ip IP address to remove. Pass 0 to remove all IP addresses. * wildcards are supported.
95 	void RemoveFromSecurityExceptionList(const char *ip);
96 
97 	/// \brief Checks to see if a given IP is in the security exception list.
98 	/// \param[in] IP address to check.
99 	/// \return True if the IP address is found in security exception list, else returns false.
100 	bool IsInSecurityExceptionList(const char *ip);
101 
102 	/// \brief Sets the maximum number of incoming connections allowed.
103 	/// \details If the number of incoming connections is less than the number of players currently connected,
104 	/// no more players will be allowed to connect.  If this is greater than the maximum number of peers allowed,
105 	/// it will be reduced to the maximum number of peers allowed.
106 	///
107 	/// Defaults to 0, meaning by default, nobody can connect to you
108 	/// \param[in] numberAllowed Maximum number of incoming connections allowed.
109 	void SetMaximumIncomingConnections( unsigned short numberAllowed );
110 
111 	/// \brief Returns the value passed to SetMaximumIncomingConnections().
112 	/// \return Maximum number of incoming connections, which is always <= maxConnections
113 	unsigned short GetMaximumIncomingConnections( void ) const;
114 
115 	/// \brief Returns how many open connections exist at this time.
116 	/// \return Number of open connections.
117 	unsigned short NumberOfConnections(void) const;
118 
119 	/// \brief Sets the password for the incoming connections.
120 	/// \details  The password must match in the call to Connect (defaults to none).
121 	/// Pass 0 to passwordData to specify no password.
122 	/// This is a way to set a low level password for all incoming connections.  To selectively reject connections, implement your own scheme using CloseConnection() to remove unwanted connections.
123 	/// \param[in] passwordData A data block that incoming connections must match.  This can be just a password, or can be a stream of data. Specify 0 for no password data
124 	/// \param[in] passwordDataLength The length in bytes of passwordData
125 	void SetIncomingPassword( const char* passwordData, int passwordDataLength );
126 
127 	/// \brief Gets the password passed to SetIncomingPassword
128 	/// \param[out] passwordData  Should point to a block large enough to hold the password data you passed to SetIncomingPassword()
129 	/// \param[in,out] passwordDataLength Maximum size of the passwordData array.  Modified to hold the number of bytes actually written.
130 	void GetIncomingPassword( char* passwordData, int *passwordDataLength  );
131 
132 	/// \brief Connect to the specified host (ip or domain name) and server port.
133 	/// \details Calling Connect and not calling SetMaximumIncomingConnections acts as a dedicated client.
134 	/// Calling both acts as a true peer.
135 	///
136 	/// This is a non-blocking connection.
137 	///
138 	/// The connection is successful when IsConnected() returns true or Receive() gets a message with the type identifier ID_CONNECTION_ACCEPTED.
139 	/// If the connection is not successful, such as a rejected connection or no response then neither of these things will happen.
140 	/// \pre Requires that you first call Initialize.
141 	/// \param[in] host Either a dotted IP address or a domain name.
142 	/// \param[in] remotePort Port to connect to on the remote machine.
143 	/// \param[in] passwordData A data block that must match the data block on the server passed to SetIncomingPassword().  This can be a string or can be a stream of data.  Use 0 for no password.
144 	/// \param[in] passwordDataLength The length in bytes of passwordData.
145 	/// \param[in] connectionSocketIndex Index into the array of socket descriptors passed to socketDescriptors in RakPeer::Startup() to determine the one to send on.
146 	/// \param[in] sendConnectionAttemptCount Number of datagrams to send to the other system to try to connect.
147 	/// \param[in] timeBetweenSendConnectionAttemptsMS Time to elapse before a datagram is sent to the other system to try to connect. After sendConnectionAttemptCount number of attempts, ID_CONNECTION_ATTEMPT_FAILED is returned.
148 	/// \param[in] timeoutTime Time to elapse before dropping the connection if a reliable message could not be sent. 0 to use the default value from SetTimeoutTime(UNASSIGNED_SYSTEM_ADDRESS);
149 	/// \return True on successful initiation. False if you are already connected to this system, a connection to the system is pending,  the domain name cannot be resolved, incorrect parameters, internal error, or too many existing peers.
150 	/// \note Returning true does not mean you are connected!
151 	/// TODO - RakNet 4 - return enum
152 	bool Connect( const char* host, unsigned short remotePort, const char *passwordData, int passwordDataLength, unsigned connectionSocketIndex=0, unsigned sendConnectionAttemptCount=12, unsigned timeBetweenSendConnectionAttemptsMS=500, RakNetTime timeoutTime=0 );
153 
154 	/// \brief Connect to the specified host (ip or domain name) and server port.
155 	/// \param[in] host Either a dotted IP address or a domain name.
156 	/// \param[in] remotePort Which port to connect to on the remote machine.
157 	/// \param[in] passwordData A data block that must match the data block on the server passed to SetIncomingPassword().  This can be a string or can be a stream of data.  Use 0 for no password.
158 	/// \param[in] passwordDataLength The length in bytes of passwordData.
159 	/// \param[in] socket A bound socket returned by another instance of RakPeerInterface.
160 	/// \param[in] sendConnectionAttemptCount Number of datagrams to send to the other system to try to connect.
161 	/// \param[in] timeBetweenSendConnectionAttemptsMS Time to elapse before a datagram is sent to the other system to try to connect. After sendConnectionAttemptCount number of attempts, ID_CONNECTION_ATTEMPT_FAILED is returned.
162 	/// \param[in] timeoutTime Time to elapse before dropping the connection if a reliable message could not be sent. 0 to use the default from SetTimeoutTime(UNASSIGNED_SYSTEM_ADDRESS);
163 	/// \return True on successful initiation. False on incorrect parameters, internal error, or too many existing peers.
164 	/// \note Returning true does not mean you arebconnected!
165 	virtual bool ConnectWithSocket(const char* host, unsigned short remotePort, const char *passwordData, int passwordDataLength, RakNetSmartPtr<RakNetSocket> socket, unsigned sendConnectionAttemptCount=12, unsigned timeBetweenSendConnectionAttemptsMS=500, RakNetTime timeoutTime=0);
166 
167 	/* /// \brief Connect to the specified network ID (Platform specific console function)
168 	/// \details Does built-in NAT traversal
169 	/// \param[in] networkServiceId Network ID structure for the online service
170 	/// \param[in] passwordData A data block that must match the data block on the server passed to SetIncomingPassword().  This can be a string or can be a stream of data.  Use 0 for no password.
171 	/// \param[in] passwordDataLength The length in bytes of passwordData.
172 	//bool Console2LobbyConnect( void *networkServiceId, const char *passwordData, int passwordDataLength );*/
173 
174 	/// \brief Stops the network threads and closes all connections.
175 	/// \param[in] blockDuration Wait time(milli seconds) for all remaining messages to go out, including ID_DISCONNECTION_NOTIFICATION.  If 0, it doesn't wait at all.
176 	/// \param[in] orderingChannel Channel on which ID_DISCONNECTION_NOTIFICATION will be sent, if blockDuration > 0.
177 	/// \param[in] disconnectionNotificationPriority Priority of sending ID_DISCONNECTION_NOTIFICATION.
178 	/// If set to 0, the disconnection notification won't be sent.
179 	void Shutdown( unsigned int blockDuration, unsigned char orderingChannel=0, PacketPriority disconnectionNotificationPriority=LOW_PRIORITY );
180 
181 	/// \brief Returns true if the network thread is running.
182 	/// \return True if the network thread is running, False otherwise
183 	bool IsActive( void ) const;
184 
185 	/// \brief Fills the array remoteSystems with the SystemAddress of all the systems we are connected to.
186 	/// \param[out] remoteSystems An array of SystemAddress structures, to be filled with the SystemAddresss of the systems we are connected to. Pass 0 to remoteSystems to get the number of systems we are connected to.
187 	/// \param[in, out] numberOfSystems As input, the size of remoteSystems array.  As output, the number of elements put into the array.
188 	bool GetConnectionList( SystemAddress *remoteSystems, unsigned short *numberOfSystems ) const;
189 
190 	/// Returns the next uint32_t that Send() will return
191 	/// \note If using RakPeer from multiple threads, this may not be accurate for your thread. Use IncrementNextSendReceipt() in that case.
192 	/// \return The next uint32_t that Send() or SendList will return
193 	virtual uint32_t GetNextSendReceipt(void);
194 
195 	/// Returns the next uint32_t that Send() will return, and increments the value by one
196 	/// \note If using RakPeer from multiple threads, pass this to forceReceipt in the send function
197 	/// \return The next uint32_t that Send() or SendList will return
198 	virtual uint32_t IncrementNextSendReceipt(void);
199 
200 	/// \brief Sends a block of data to the specified system that you are connected to.
201 	/// \note This function only works while the connected.
202 	/// \note The first byte should be a message identifier starting at ID_USER_PACKET_ENUM.
203 	/// \param[in] data Block of data to send.
204 	/// \param[in] length Size in bytes of the data to send.
205 	/// \param[in] priority Priority level to send on.  See PacketPriority.h
206 	/// \param[in] reliability How reliably to send this data.  See PacketPriority.h
207 	/// \param[in] orderingChannel When using ordered or sequenced messages, the channel to order these on. Messages are only ordered relative to other messages on the same stream.
208 	/// \param[in] systemIdentifier Who to send this packet to, or in the case of broadcasting who not to send it to. Pass either a SystemAddress structure or a RakNetGUID structure. Use UNASSIGNED_SYSTEM_ADDRESS or to specify none
209 	/// \param[in] broadcast True to send this packet to all connected systems. If true, then systemAddress specifies who not to send the packet to.
210 	/// \param[in] forceReceipt If 0, will automatically determine the receipt number to return. If non-zero, will return what you give it.
211 	/// \return 0 on bad input. Otherwise a number that identifies this message. If \a reliability is a type that returns a receipt, on a later call to Receive() you will get ID_SND_RECEIPT_ACKED or ID_SND_RECEIPT_LOSS with bytes 1-4 inclusive containing this number
212 	uint32_t Send( const char *data, const int length, PacketPriority priority, PacketReliability reliability, char orderingChannel, const AddressOrGUID systemIdentifier, bool broadcast, uint32_t forceReceipt=0 );
213 
214 	/// \brief "Send" to yourself rather than a remote system.
215 	/// \details The message will be processed through the plugins and returned to the game as usual.
216 	/// This function works anytime
217 	/// \note The first byte should be a message identifier starting at ID_USER_PACKET_ENUM
218 	/// \param[in] data Block of data to send.
219 	/// \param[in] length Size in bytes of the data to send.
220 	void SendLoopback( const char *data, const int length );
221 
222 	/// \brief Sends a block of data to the specified system that you are connected to.
223 	///
224 	/// Same as the above version, but takes a BitStream as input.
225 	/// \param[in] bitStream Bitstream to send
226 	/// \param[in] priority Priority level to send on.  See PacketPriority.h
227 	/// \param[in] reliability How reliably to send this data.  See PacketPriority.h
228 	/// \param[in] orderingChannel Channel to order the messages on, when using ordered or sequenced messages. Messages are only ordered relative to other messages on the same stream.
229 	/// \param[in] systemIdentifier System Address or RakNetGUID to send this packet to, or in the case of broadcasting, the address not to send it to.  Use UNASSIGNED_SYSTEM_ADDRESS to specify none.
230 	/// \param[in] broadcast True to send this packet to all connected systems. If true, then systemAddress specifies who not to send the packet to.
231 	/// \param[in] forceReceipt If 0, will automatically determine the receipt number to return. If non-zero, will return what you give it.
232 	/// \return 0 on bad input. Otherwise a number that identifies this message. If \a reliability is a type that returns a receipt, on a later call to Receive() you will get ID_SND_RECEIPT_ACKED or ID_SND_RECEIPT_LOSS with bytes 1-4 inclusive containing this number
233 	/// \note COMMON MISTAKE: When writing the first byte, bitStream->Write((unsigned char) ID_MY_TYPE) be sure it is casted to a byte, and you are not writing a 4 byte enumeration.
234 	uint32_t Send( const RakNet::BitStream * bitStream, PacketPriority priority, PacketReliability reliability, char orderingChannel, const AddressOrGUID systemIdentifier, bool broadcast, uint32_t forceReceipt=0 );
235 
236 	/// \brief Sends multiple blocks of data, concatenating them automatically.
237 	///
238 	/// This is equivalent to:
239 	/// RakNet::BitStream bs;
240 	/// bs.WriteAlignedBytes(block1, blockLength1);
241 	/// bs.WriteAlignedBytes(block2, blockLength2);
242 	/// bs.WriteAlignedBytes(block3, blockLength3);
243 	/// Send(&bs, ...)
244 	///
245 	/// This function only works when connected.
246 	/// \param[in] data An array of pointers to blocks of data
247 	/// \param[in] lengths An array of integers indicating the length of each block of data
248 	/// \param[in] numParameters Length of the arrays data and lengths
249 	/// \param[in] priority Priority level to send on.  See PacketPriority.h
250 	/// \param[in] reliability How reliably to send this data.  See PacketPriority.h
251 	/// \param[in] orderingChannel Channel to order the messages on, when using ordered or sequenced messages. Messages are only ordered relative to other messages on the same stream.
252 	/// \param[in] systemIdentifier System Address or RakNetGUID to send this packet to, or in the case of broadcasting, the address not to send it to.  Use UNASSIGNED_SYSTEM_ADDRESS to specify none.
253 	/// \param[in] broadcast True to send this packet to all connected systems. If true, then systemAddress specifies who not to send the packet to.
254 	/// \param[in] forceReceipt If 0, will automatically determine the receipt number to return. If non-zero, will return what you give it.
255 	/// \return 0 on bad input. Otherwise a number that identifies this message. If \a reliability is a type that returns a receipt, on a later call to Receive() you will get ID_SND_RECEIPT_ACKED or ID_SND_RECEIPT_LOSS with bytes 1-4 inclusive containing this number
256 	/// \note Doesn't support the router plugin.
257 	uint32_t SendList( const char **data, const int *lengths, const int numParameters, PacketPriority priority, PacketReliability reliability, char orderingChannel, const AddressOrGUID systemIdentifier, bool broadcast, uint32_t forceReceipt=0 );
258 
259 	/// \brief Gets a message from the incoming message queue.
260 	/// \details Use DeallocatePacket() to deallocate the message after you are done with it.
261 	/// User-thread functions, such as RPC calls and the plugin function PluginInterface::Update occur here.
262 	/// \return 0 if no packets are waiting to be handled, otherwise a pointer to a packet.
263 	/// \note COMMON MISTAKE: Be sure to call this in a loop, once per game tick, until it returns 0. If you only process one packet per game tick they will buffer up.
264 	/// \sa RakNetTypes.h contains struct Packet.
265 	Packet* Receive( void );
266 
267 	/// \brief Call this to deallocate a message returned by Receive() when you are done handling it.
268 	/// \param[in] packet Message to deallocate.
269 	void DeallocatePacket( Packet *packet );
270 
271 	/// \brief Return the total number of connections we are allowed.
272 	/// \return Total number of connections allowed.
273 	unsigned short GetMaximumNumberOfPeers( void ) const;
274 
275 	// --------------------------------------------------------------------------------------------Remote Procedure Call Functions - Functions to initialize and perform RPC--------------------------------------------------------------------------------------------
276 	/// \ingroup RAKNET_RPC
277 	/// \brief Register a C or static member function as available for calling a remote procedure call.
278 	/// \param[in] uniqueID A null-terminated unique string to identify this procedure.  See RegisterClassMemberRPC() for class member functions.
279 	/// \param[in] functionPointer(...) The name of the function to be used as a function pointer. This can be called whether active or not, and registered functions stay registered unless unregistered
280 	/// \deprecated Use RakNet::RPC3
281 	void RegisterAsRemoteProcedureCall( const char* uniqueID, void ( *functionPointer ) ( RPCParameters *rpcParms ) );
282 
283 	/// \ingroup RAKNET_RPC
284 	/// \brief Register a C++ member function as available for calling as a remote procedure call.
285 	/// \param[in] uniqueID A null terminated string to identify this procedure. It is recommended to use the macro REGISTER_CLASS_MEMBER_RPC to create the string.  Use RegisterAsRemoteProcedureCall() for static functions.
286 	/// \param[in] functionPointer The name of the function to be used as a function pointer. This can be called whether active or not, and registered functions stay registered unless unregistered with UnregisterAsRemoteProcedureCall.
287 	/// \sa The sample ObjectMemberRPC.cpp
288 	/// \deprecated Use RakNet::RPC3
289 	void RegisterClassMemberRPC( const char* uniqueID, void *functionPointer );
290 
291 	/// \ingroup RAKNET_RPC
292 	/// \brief Unregisters a C function as available for calling as a remote procedure call that was formerly registered with RegisterAsRemoteProcedureCall. Only call offline.
293 	/// \param[in] uniqueID A string of only letters to identify this procedure.  Recommended you use the macro CLASS_MEMBER_ID for class member functions.
294 		/// \deprecated Use RakNet::RPC3
295 	void UnregisterAsRemoteProcedureCall( const char* uniqueID );
296 
297 	/// \ingroup RAKNET_RPC
298 	/// \brief Used by Object member RPC to lookup objects given that object's ID.
299 	/// Also used by the ReplicaManager plugin
300 	/// \param[in] An instance of NetworkIDManager to use for the loookup.
301 	void SetNetworkIDManager( NetworkIDManager *manager );
302 
303 	/// \return Returns the value passed to SetNetworkIDManager or 0 if never called.
304 	NetworkIDManager *GetNetworkIDManager(void) const;
305 
306 	/// ------------------------------------------- Deprecated -------------------------
307 	/// \ingroup RAKNET_RPC
308 	/// Calls a C function on the remote system that was already registered using RegisterAsRemoteProcedureCall().
309 	/// \pre To use object member RPC (networkID!=UNASSIGNED_OBJECT_ID), The recipient must have called SetNetworkIDManager so the system can handle the object lookups
310 	/// \param[in] uniqueID A NULL terminated string identifying the function to call.  Recommended you use the macro CLASS_MEMBER_ID for class member functions.
311 	/// \param[in] data The data to send
312 	/// \param[in] bitLength The number of bits of \a data
313 	/// \param[in] priority What priority level to send on. See PacketPriority.h.
314 	/// \param[in] reliability How reliability to send this data. See PacketPriority.h.
315 	/// \param[in] orderingChannel When using ordered or sequenced message, what channel to order these on.
316 	/// \param[in] systemAddress Who to send this message to, or in the case of broadcasting who not to send it to.  Pass either a SystemAddress structure or a RakNetGUID structure. Use UNASSIGNED_SYSTEM_ADDRESS or to specify none
317 	/// \param[in] broadcast True to send this packet to all connected systems. If true, then systemAddress specifies who not to send the packet to.
318 	/// \param[in] includedTimestamp Pass a timestamp if you wish, to be adjusted in the usual fashion as per ID_TIMESTAMP.  Pass 0 to not include a timestamp.
319 	/// \param[in] networkID For static functions, pass UNASSIGNED_NETWORK_ID.  For member functions, you must derive from NetworkIDObject and pass the value returned by NetworkIDObject::GetNetworkID for that object.
320 	/// \param[in] replyFromTarget If 0, this function is non-blocking.  Otherwise it will block while waiting for a reply from the target procedure, which should be remotely written to RPCParameters::replyToSender and copied to replyFromTarget.  The block will return early on disconnect or if the sent packet is unreliable and more than 3X the ping has elapsed.
321 	/// \return True on a successful packet send (this does not indicate the recipient performed the call), false on failure
322 	/// \deprecated Use RakNet::RPC3. This only correctly works for C functions. For C++, it only works for Windows. It is less flexible than RPC3
323 	/// ------------------------------------------- Deprecated -------------------------
324 	bool RPC( const char* uniqueID, const char *data, BitSize_t bitLength, PacketPriority priority, PacketReliability reliability, char orderingChannel, const AddressOrGUID systemIdentifier, bool broadcast, RakNetTime *includedTimestamp, NetworkID networkID, RakNet::BitStream *replyFromTarget );
325 
326 	/// ------------------------------------------- Deprecated -------------------------
327 	/// \ingroup RAKNET_RPC
328 	/// \brief Calls a C function on the remote system that was already registered using RegisterAsRemoteProcedureCall.
329 	/// \details If you want that function to return data you should call RPC from that system in the same way.Returns true on a successful packet
330 	/// send (this does not indicate the recipient performed the call), false on failure.
331 	/// \pre To use object member RPC (networkID!=UNASSIGNED_OBJECT_ID), the recipient must have called SetNetworkIDManager so the system can handle the object lookups.
332 	/// \param[in] uniqueID A NULL terminated string identifying the function to call.  Recommended you use the macro CLASS_MEMBER_ID for class member functions.
333 	/*/// \param[in] data The data to send
334 	/// \param[in] bitLength The number of bits of \a data*/
335 	///	\param[in] bitStream The bit stream to send.
336 	/// \param[in] priority What priority level to send on. See PacketPriority.h.
337 	/// \param[in] reliability How reliably to send this data. See PacketPriority.h.
338 	/// \param[in] orderingChannel When using ordered or sequenced message, what channel to order these on.
339 	/// \param[in] systemAddress Who to send this message to, or in the case of broadcasting who not to send it to.  Pass either a SystemAddress structure or a RakNetGUID structure. Use UNASSIGNED_SYSTEM_ADDRESS or to specify none
340 	/// \param[in] broadcast True to send this packet to all connected systems. If true, then systemAddress specifies who not to send the packet to.
341 	/// \param[in] includedTimestamp Pass a timestamp if you wish, to be adjusted in the usual fashion as per ID_TIMESTAMP.  Pass 0 to not include a timestamp.
342 	/// \param[in] networkID For static functions, pass UNASSIGNED_NETWORK_ID.  For member functions, you must derive from NetworkIDObject and pass the value returned by NetworkIDObject::GetNetworkID for that object.
343 	/// \param[in] replyFromTarget If 0, this function is non-blocking.  Otherwise it will block while waiting for a reply from the target procedure, which should be remotely written to RPCParameters::replyToSender and copied to replyFromTarget.  The block will return early on disconnect or if the sent packet is unreliable and more than 3X the ping has elapsed.
344 	/// \return True on a successful packet send (this does not indicate the recipient performed the call), false on failure
345 	/// \deprecated Use RakNet::RPC3. This only correctly works for C functions. For C++, it only works for Windows. It is less flexible than RPC3
346 	/// ------------------------------------------- Deprecated -------------------------
347 	bool RPC( const char* uniqueID, const RakNet::BitStream *bitStream, PacketPriority priority, PacketReliability reliability, char orderingChannel, const AddressOrGUID systemIdentifier, bool broadcast, RakNetTime *includedTimestamp, NetworkID networkID, RakNet::BitStream *replyFromTarget );
348 
349 	// -------------------------------------------------------------------------------------------- Connection Management Functions--------------------------------------------------------------------------------------------
350 	/// \brief Close the connection to another host (if we initiated the connection it will disconnect, if they did it will kick them out).
351 	/// \details This method closes the connection irrespective of who initiated the connection.
352 	/// \param[in] target Which system to close the connection to.
353 	/// \param[in] sendDisconnectionNotification True to send ID_DISCONNECTION_NOTIFICATION to the recipient.  False to close it silently.
354 	/// \param[in] channel Which ordering channel to send the disconnection notification on, if any
355 	/// \param[in] disconnectionNotificationPriority Priority to send ID_DISCONNECTION_NOTIFICATION on.
356 	void CloseConnection( const SystemAddress target, bool sendDisconnectionNotification, unsigned char orderingChannel=0, PacketPriority disconnectionNotificationPriority=LOW_PRIORITY );
357 
358 	/// \brief Cancel a pending connection attempt.
359 	/// \details If we are already connected, the connection stays open
360 	/// \param[in] target Target system to cancel.
361 	void CancelConnectionAttempt( const SystemAddress target );
362 
363 	/// Returns if a particular systemAddress has a pending or in progress connection attempt
364 	/// \param[in] systemAddress The SystemAddress we are referring to
365 	bool IsConnectionAttemptPending( const SystemAddress systemAddress );
366 
367 	/// \brief Returns if a particular systemAddress is connected to us.
368 	///	\note This can also be made to return true if we are in the process of connecting.
369 	/// \param[in] systemAddress The SystemAddress we are referring to
370 	/// \param[in] includeInProgress If true, also return true for connections that are in progress but haven't completed
371 	/// \param[in] includeDisconnecting If true, also return true for connections that are in the process of disconnecting
372 	/// \note This locks a mutex, do not call too frequently during connection attempts with includeInProgress==true or you may cause the attempt to take longer and fail
373 	/// \return True if this system is connected and active, false otherwise.
374 	bool IsConnected(const AddressOrGUID systemIdentifier, bool includeInProgress=false, bool includeDisconnecting=false);
375 
376 	/// \brief Given \a systemAddress, returns its index into remoteSystemList.
377 	/// \details Values range from 0 to the maximum number of players allowed - 1.
378 	/// This includes systems which were formerly connected, but are now not connected.
379 	/// \param[in] systemAddress The SystemAddress we are referring to
380 	/// \return The index of this SystemAddress or -1 on system not found.
381 	int GetIndexFromSystemAddress( const SystemAddress systemAddress ) const;
382 
383 	/// \brief Given \a index into remoteSystemList, will return a SystemAddress.
384 	/// This function is only useful for looping through all systems.
385 	///
386 	/// \param[in] index Index should range between 0 and the maximum number of players allowed - 1.
387 	/// \return The SystemAddress structure corresponding to \a index in remoteSystemList.
388 	SystemAddress GetSystemAddressFromIndex( int index );
389 
390 	/// \brief Same as GetSystemAddressFromIndex but returns RakNetGUID
391 	/// \param[in] index Index should range between 0 and the maximum number of players allowed - 1.
392 	/// \return The RakNetGUID
393 	RakNetGUID GetGUIDFromIndex( int index );
394 
395 	/// \brief Same as calling GetSystemAddressFromIndex and GetGUIDFromIndex for all systems, but more efficient
396 	/// Indices match each other, so \a addresses[0] and \a guids[0] refer to the same system
397 	/// \param[out] addresses All system addresses. Size of the list is the number of connections. Size of the \a addresses list will match the size of the \a guids list.
398 	/// \param[out] guids All guids. Size of the list is the number of connections. Size of the list will match the size of the \a addresses list.
399 	void GetSystemList(DataStructures::List<SystemAddress> &addresses, DataStructures::List<RakNetGUID> &guids);
400 
401 	/// \brief Bans an IP from connecting.
402 	/// \details Banned IPs persist between connections but are not saved on shutdown nor loaded on startup.
403 	/// \param[in] IP Dotted IP address. You can use * for a wildcard address, such as 128.0.0. * will ban all IP addresses starting with 128.0.0.
404 	/// \param[in] milliseconds Gives time in milli seconds for a temporary ban of the IP address.  Use 0 for a permanent ban.
405 	void AddToBanList( const char *IP, RakNetTime milliseconds=0 );
406 
407 	/// \brief Allows a previously banned IP to connect.
408 	/// param[in] Dotted IP address. You can use * as a wildcard. An IP such as 128.0.0.* will ban all IP addresses starting with 128.0.0.
409 	void RemoveFromBanList( const char *IP );
410 
411 	/// \brief Allows all previously banned IPs to connect.
412 	void ClearBanList( void );
413 
414 	/// \brief Returns true or false indicating if a particular IP is banned.
415 	/// \param[in] IP Dotted IP address.
416 	/// \return True if IP matches any IPs in the ban list, accounting for any wildcards. False otherwise.
417 	bool IsBanned( const char *IP );
418 
419 	/// \brief Enable or disable allowing frequent connections from the same IP adderss
420 	/// \details This is a security measure which is disabled by default, but can be set to true to prevent attackers from using up all connection slots.
421 	/// \param[in] b True to limit connections from the same ip to at most 1 per 100 milliseconds.
422 	void SetLimitIPConnectionFrequency(bool b);
423 
424 	// --------------------------------------------------------------------------------------------Pinging Functions - Functions dealing with the automatic ping mechanism--------------------------------------------------------------------------------------------
425 	/// Send a ping to the specified connected system.
426 	/// \pre The sender and recipient must already be started via a successful call to Startup()
427 	/// \param[in] target Which system to ping
428 	void Ping( const SystemAddress target );
429 
430 	/// \brief Send a ping to the specified unconnected system.
431 	/// \details The remote system, if it is Initialized, will respond with ID_PONG followed by sizeof(RakNetTime) containing the system time the ping was sent. Default is 4 bytes - See __GET_TIME_64BIT in RakNetTypes.h
432 	/// System should reply with ID_PONG if it is active
433 	/// \param[in] host Either a dotted IP address or a domain name.  Can be 255.255.255.255 for LAN broadcast.
434 	/// \param[in] remotePort Which port to connect to on the remote machine.
435 	/// \param[in] onlyReplyOnAcceptingConnections Only request a reply if the remote system is accepting connections
436 	/// \param[in] connectionSocketIndex Index into the array of socket descriptors passed to socketDescriptors in RakPeer::Startup() to send on.
437 	/// \return true on success, false on failure (unknown hostname)
438 	bool Ping( const char* host, unsigned short remotePort, bool onlyReplyOnAcceptingConnections, unsigned connectionSocketIndex=0 );
439 
440 	/// \brief Returns the average of all ping times read for the specific system or -1 if none read yet
441 	/// \param[in] systemAddress Which system we are referring to
442 	/// \return The ping time for this system, or -1
443 	int GetAveragePing( const AddressOrGUID systemIdentifier );
444 
445 	/// \brief Returns the last ping time read for the specific system or -1 if none read yet.
446 	/// \param[in] systemAddress Which system we are referring to
447 	/// \return The last ping time for this system, or -1.
448 	int GetLastPing( const AddressOrGUID systemIdentifier ) const;
449 
450 	/// \brief Returns the lowest ping time read or -1 if none read yet.
451 	/// \param[in] systemAddress Which system we are referring to
452 	/// \return The lowest ping time for this system, or -1.
453 	int GetLowestPing( const AddressOrGUID systemIdentifier ) const;
454 
455 	/// Ping the remote systems every so often, or not. Can be called anytime.
456 	/// By default this is true if GET_TIME_SPIKE_LIMIT is non-zero from RakNetDefines, false otherwise
457 	/// It would be true by default to prevent timestamp drift, since in the event of a clock spike, the timestamp deltas would no longer be accurate
458 	/// \param[in] doPing True to start occasional pings.  False to stop them.
459 	void SetOccasionalPing( bool doPing );
460 
461 	// --------------------------------------------------------------------------------------------Static Data Functions - Functions dealing with API defined synchronized memory--------------------------------------------------------------------------------------------
462 	/// \brief Sets the data to send along with a LAN server discovery or offline ping reply.
463 	/// \param[in] data Block of data to send, or 0 for none
464 	/// \param[in] length Length of the data in bytes, or 0 for none
465 	/// \note \a length should be under 400 bytes, as a security measure against flood attacks
466 	/// \sa Ping.cpp
467 	void SetOfflinePingResponse( const char *data, const unsigned int length );
468 
469 	/// \brief Returns pointers to a copy of the \a data passed to SetOfflinePingResponse.
470 	/// \param[out] data A pointer to a copy of the data passed to SetOfflinePingResponse()
471 	/// \param[out] length A pointer filled in with the length parameter passed to SetOfflinePingResponse()
472 	/// \sa SetOfflinePingResponse
473 	void GetOfflinePingResponse( char **data, unsigned int *length );
474 
475 	//--------------------------------------------------------------------------------------------Network Functions - Functions dealing with the network in general--------------------------------------------------------------------------------------------
476 	/// \brief Returns the unique address identifier that represents you or another system on the the network and is based on your local IP / port.
477 	/// \param[in] systemAddress Use UNASSIGNED_SYSTEM_ADDRESS to get your behind-LAN address. Use a connected system to get their behind-LAN address
478 	/// \param[in] index When you have multiple internal IDs, which index to return? Currently limited to MAXIMUM_NUMBER_OF_INTERNAL_IDS (so the maximum value of this variable is MAXIMUM_NUMBER_OF_INTERNAL_IDS-1)
479 	/// \return Identifier of your system internally, which may not be how other systems see if you if you are behind a NAT or proxy
480 	SystemAddress GetInternalID( const SystemAddress systemAddress=UNASSIGNED_SYSTEM_ADDRESS, const int index=0 ) const;
481 
482 	/// \brief Returns the unique address identifier that represents the target on the the network and is based on the target's external IP / port.
483 	/// \param[in] target The SystemAddress of the remote system. Usually the same for all systems, unless you have two or more network cards.
484 	SystemAddress GetExternalID( const SystemAddress target ) const;
485 
486 	/// \brief  Given a connected system address, this method gives the unique GUID representing that instance of RakPeer.
487 	/// This will be the same on all systems connected to that instance of RakPeer, even if the external system addresses are different.
488 	/// Complexity is O(log2(n)).
489 	/// If \a input is UNASSIGNED_SYSTEM_ADDRESS, will return your own GUID
490 	/// \pre Call Startup() first, or the function will return UNASSIGNED_RAKNET_GUID
491 	/// \param[in] input The system address of the target system we are connected to.
492 	const RakNetGUID& GetGuidFromSystemAddress( const SystemAddress input ) const;
493 
494 	/// \brief Gives the system address of a connected system, given its GUID.
495 	/// The GUID will be the same on all systems connected to that instance of RakPeer, even if the external system addresses are different.
496 	/// Currently O(log(n)), but this may be improved in the future
497 	/// If \a input is UNASSIGNED_RAKNET_GUID, UNASSIGNED_SYSTEM_ADDRESS is returned.
498 	/// \param[in] input The RakNetGUID of the target system.
499 	SystemAddress GetSystemAddressFromGuid( const RakNetGUID input ) const;
500 
501 	/// \brief Set the time, in MS, to use before considering ourselves disconnected after not being able to deliver a reliable message.
502 	/// \details Default time is 10,000 or 10 seconds in release and 30,000 or 30 seconds in debug.
503     /// \param[in] timeMS Time, in MS
504 	/// \param[in] target SystemAddress structure of the target system. Pass UNASSIGNED_SYSTEM_ADDRESS for all systems.
505 	void SetTimeoutTime( RakNetTime timeMS, const SystemAddress target );
506 
507 	/// \brief Returns the Timeout time for the given system.
508 	/// \param[in] target Target system to get the TimeoutTime for. Pass UNASSIGNED_SYSTEM_ADDRESS to get the default value.
509 	/// \return Timeout time for a given system.
510 	RakNetTime GetTimeoutTime( const SystemAddress target );
511 
512 	/*/// \deprecated 8/12/09
513 	/// \brief MTU automatically calculated during connection process
514 	/// \details Set the MTU per datagram.  It's important to set this correctly - otherwise packets will be needlessly split, decreasing performance and throughput.
515 	/// Maximum allowed size is MAXIMUM_MTU_SIZE.
516 	/// Too high of a value will cause packets not to arrive at worst and be fragmented at best.
517 	/// Too low of a value will split packets unnecessarily.
518 	/// sa MTUSize.h
519 	/// \param[in] size The MTU size
520 	/// \param[in] target Which system to set this for.  UNASSIGNED_SYSTEM_ADDRESS to set the default, for new systems
521 	/// \pre Can only be called when not connected.
522 	/// \return false on failure (we are connected), else true
523 	/// bool SetMTUSize( int size, const SystemAddress target );*/
524 
525 	/// \brief Returns the current MTU size
526 	/// \param[in] target Which system to get MTU for.  UNASSIGNED_SYSTEM_ADDRESS to get the default
527 	/// \return The current MTU size of the target system.
528 	int GetMTUSize( const SystemAddress target ) const;
529 
530 	/// \brief Returns the number of IP addresses this system has internally.
531 	/// \details Get the actual addresses from GetLocalIP()
532 	unsigned GetNumberOfAddresses( void );
533 
534 	/// Returns an IP address at index 0 to GetNumberOfAddresses-1 in ipList array.
535 	/// \param[in] index index into the list of IP addresses
536 	/// \return The local IP address at this index
537 	const char* GetLocalIP( unsigned int index );
538 
539 	/// Is this a local IP?
540 	/// Checks if this ip is in the ipList array.
541 	/// \param[in] An IP address to check, excluding the port.
542 	/// \return True if this is one of the IP addresses returned by GetLocalIP
543 	bool IsLocalIP( const char *ip );
544 
545 	/// \brief Allow or disallow connection responses from any IP.
546 	/// \details Normally this should be false, but may be necessary when connecting to servers with multiple IP addresses.
547 	/// \param[in] allow - True to allow this behavior, false to not allow. Defaults to false. Value persists between connections.
548 	void AllowConnectionResponseIPMigration( bool allow );
549 
550 	/// \brief Sends a one byte message ID_ADVERTISE_SYSTEM to the remote unconnected system.
551 	/// This will send our external IP outside the LAN along with some user data to the remote system.
552 	/// \pre The sender and recipient must already be started via a successful call to Initialize
553 	/// \param[in] host Either a dotted IP address or a domain name
554 	/// \param[in] remotePort Which port to connect to on the remote machine.
555 	/// \param[in] data Optional data to append to the packet.
556 	/// \param[in] dataLength Length of data in bytes.  Use 0 if no data.
557 	/// \param[in] connectionSocketIndex Index into the array of socket descriptors passed to socketDescriptors in RakPeer::Startup() to send on.
558 	/// \return False if IsActive()==false or the host is unresolvable. True otherwise.
559 	bool AdvertiseSystem( const char *host, unsigned short remotePort, const char *data, int dataLength, unsigned connectionSocketIndex=0 );
560 
561 	/// \brief Controls how often to return ID_DOWNLOAD_PROGRESS for large message downloads.
562 	/// \details ID_DOWNLOAD_PROGRESS is returned to indicate a new partial message chunk, roughly the MTU size, has arrived.
563 	/// As it can be slow or cumbersome to get this notification for every chunk, you can set the interval at which it is returned.
564 	/// Defaults to 0 (never return this notification).
565 	/// \param[in] interval How many messages to use as an interval before a download progress notification is returned.
566 	void SetSplitMessageProgressInterval(int interval);
567 
568 	/// \brief Returns what was passed to SetSplitMessageProgressInterval().
569 	/// \return Number of messages to be recieved before a download progress notification is returned. Default to 0.
570 	int GetSplitMessageProgressInterval(void) const;
571 
572 	/// \brief Set how long to wait before giving up on sending an unreliable message.
573 	/// Useful if the network is clogged up.
574 	/// Set to 0 or less to never timeout.  Defaults to 0.
575 	/// \param[in] timeoutMS How many ms to wait before simply not sending an unreliable message.
576 	void SetUnreliableTimeout(RakNetTime timeoutMS);
577 
578 	/// \brief Send a message to a host, with the IP socket option TTL set to 3.
579 	/// \details This message will not reach the host, but will open the router.
580 	/// \param[in] host The address of the remote host in dotted notation.
581 	/// \param[in] remotePort The port number to send to.
582 	/// \param[in] ttl Max hops of datagram, set to 3
583 	/// \param[in] connectionSocketIndex userConnectionSocketIndex.
584 	/// \remarks Used for NAT-Punchthrough
585 	void SendTTL( const char* host, unsigned short remotePort, int ttl, unsigned connectionSocketIndex=0 );
586 
587 	// --------------------------------------------------------------------------------------------Compression Functions - Functions related to the compression layer--------------------------------------------------------------------------------------------
588 	/// \brief Enables or disables frequency table tracking.
589 	/// \details This is required to get a frequency table, which is used in GenerateCompressionLayer().
590 	/// This value persists between connect calls and defaults to false (no frequency tracking).
591 	/// \pre You can call this at any time - however you SHOULD only call it when disconnected.  Otherwise you will only trackpart of the values sent over the network.
592 	/// \param[in] doCompile True to enable tracking
593 	void SetCompileFrequencyTable( bool doCompile );
594 
595 	/// \brief Returns the frequency of outgoing bytes into outputFrequencyTable
596 	/// The purpose is to save to file as either a master frequency table from a sample game session for passing to
597 	/// GenerateCompressionLayer()
598 	/// \pre You should only call this when disconnected. Requires that you first enable data frequency tracking by calling SetCompileFrequencyTable(true)
599 	/// \param[out] outputFrequencyTable  The frequency of each corresponding byte
600 	/// \return False (failure) if connected or if frequency table tracking is not enabled. Otherwise true (success)
601 	bool GetOutgoingFrequencyTable( unsigned int outputFrequencyTable[ 256 ] );
602 
603 	/// \brief This is an optional function to generate the compression layer based on the input frequency table.
604 	/// \details If you want to use it you should call this twice - once with inputLayer as true and once as false.
605 	/// The frequency table passed here with inputLayer=true should match the frequency table on the recipient with inputLayer=false.
606 	/// Likewise, the frequency table passed here with inputLayer=false should match the frequency table on the recipient with inputLayer=true.
607 	/// Calling this function when there is an existing layer will overwrite the old layer.
608 	/// \pre You should only call this when disconnected.
609 	/// \param[in] inputFrequencyTable A frequency table for your data returned from GetOutgoingFrequencyTable()
610 	/// \param[in] inputLayer Whether inputFrequencyTable represents incoming data from other systems (true) or outgoing data from this system (false).
611 	/// \return false (failure) if connected.  Otherwise true (success)
612 	/// \sa Compression.cpp
613 	bool GenerateCompressionLayer( unsigned int inputFrequencyTable[ 256 ], bool inputLayer );
614 
615 	/// \brief Delete the output or input layer as specified.
616 	///
617 	/// This is not necessary to call and is only useful for freeing memory.
618 	/// \pre You should only call this when disconnected.
619 	/// \param[in] inputLayer True to mean the inputLayer, false to mean the output layer.
620 	/// \return False (failure) if connected.  Otherwise True (success).
621 	bool DeleteCompressionLayer( bool inputLayer );
622 
623 	/// \brief Returns the compression ratio.
624 	/// \details A low compression ratio is good. Compression is defined for outgoing data.
625 	/// \return The compression ratio
626 	float GetCompressionRatio( void ) const;
627 
628 	/// \brief Returns the decompression ratio.
629 	/// \details A high decompression ratio is good. Decompression ratio is defined for incoming data.
630 	/// \return The decompression ratio
631 	float GetDecompressionRatio( void ) const;
632 
633 	// -------------------------------------------------------------------------------------------- Plugin Functions--------------------------------------------------------------------------------------------
634 	/// \brief Attatches a Plugin interface to an instance of the base class (RakPeer or PacketizedTCP) to run code automatically on message receipt in the Receive call.
635 	/// \note If plugins have dependencies on each other then the order does matter - for example the router plugin should go first because it might route messages for other plugins.
636 	/// \param[in] messageHandler Pointer to the plugin to attach.
637 	void AttachPlugin( PluginInterface2 *plugin );
638 
639 	/// \brief Detaches a Plugin interface from the instance of the base class (RakPeer or PacketizedTCP) it is attached to.
640 	///	\details This method disables the plugin code from running automatically on base class's updates or message receipt.
641 	/// \param[in] messageHandler Pointer to a plugin to detach.
642 	void DetachPlugin( PluginInterface2 *messageHandler );
643 
644 	// --------------------------------------------------------------------------------------------Miscellaneous Functions--------------------------------------------------------------------------------------------
645 	/// \brief Puts a message back in the receive queue in case you don't want to deal with it immediately.
646 	/// \param[in] packet The pointer to the packet you want to push back.
647 	/// \param[in] pushAtHead True to push the packet at the start of the queue so that the next receive call returns it.  False to push it at the end of the queue.
648 	/// \note Setting pushAtHead to false end makes the packets out of order.
649 	void PushBackPacket( Packet *packet, bool pushAtHead );
650 
651 	/// ------------------------------------------- Deprecated -------------------------
652 	/// \Internal
653 	/// \deprecated This was added without considering proper architecture
654 	// \param[in] routerInterface The router to use to route messages to systems not directly connected to this system.
655 	/// ------------------------------------------- Deprecated -------------------------
656 	void SetRouterInterface( RouterInterface *routerInterface );
657 
658 	/// \Internal
659 	/// \deprecated This was added without considering proper architecture
660 	// \param[in] routerInterface The router to use to route messages to systems not directly connected to this system.
661 	void RemoveRouterInterface( RouterInterface *routerInterface );
662 
663 	/// \internal
664 	/// \brief For a given system identified by \a guid, change the SystemAddress to send to.
665 	/// \param[in] guid The connection we are referring to
666 	/// \param[in] systemAddress The new address to send to
667 	void ChangeSystemAddress(RakNetGUID guid, SystemAddress systemAddress);
668 
669 	/// \brief Returns a packet for you to write to if you want to create a Packet for some reason.
670 	/// You can add it to the receive buffer with PushBackPacket
671 	/// \param[in] dataSize How many bytes to allocate for the buffer
672 	/// \return A packet.
673 	Packet* AllocatePacket(unsigned dataSize);
674 
675 	/// \brief Get the socket used with a particular active connection.
676 	/// The smart pointer reference counts the RakNetSocket object, so the socket will remain active as long as the smart pointer does, even if RakNet were to shutdown or close the connection.
677 	/// \note This sends a query to the thread and blocks on the return value for up to one second. In practice it should only take a millisecond or so.
678 	/// \param[in] target Which system.
679 	/// \return A smart pointer object containing the socket information about the target. Be sure to check IsNull() which is returned if the update thread is unresponsive, shutting down, or if this system is not connected.
680 	virtual RakNetSmartPtr<RakNetSocket> GetSocket( const SystemAddress target );
681 
682 	/// \brief Gets all sockets in use.
683 	/// \note This sends a query to the thread and blocks on the return value for up to one second. In practice it should only take a millisecond or so.
684 	/// \param[out] sockets List of RakNetSocket structures in use. Sockets will not be closed until \a sockets goes out of scope
685 	virtual void GetSockets( DataStructures::List<RakNetSmartPtr<RakNetSocket> > &sockets );
686 
687 	/// \internal
688 	virtual void WriteOutOfBandHeader(RakNet::BitStream *bitStream);
689 
690 	/// If you need code to run in the same thread as RakNet's update thread, this function can be used for that
691 	/// \param[in] _userUpdateThreadPtr C callback function
692 	/// \param[in] _userUpdateThreadData Passed to C callback function
693 	virtual void SetUserUpdateThread(void (*_userUpdateThreadPtr)(RakPeerInterface *, void *), void *_userUpdateThreadData);
694 
695 	// --------------------------------------------------------------------------------------------Network Simulator Functions--------------------------------------------------------------------------------------------
696 	/// \brief Adds simulated ping and packet loss to the outgoing data flow.
697 	/// \details To simulate bi-directional ping and packet loss, you should call this on both the sender and the recipient, with half the total ping and maxSendBPS values on each.
698 	/// \deprecated Use http://www.jenkinssoftware.com/raknet/forum/index.php?topic=1671.0 instead.
699 	/// \note You can exclude network simulator code with the  #define _RELEASE to decrease code size.
700 	/// \note Doesn't work past version 3.6201
701 	/// \param[in] packetloss Chance to lose a packet. Ranges from 0 to 1.
702 	/// \param[in] minExtraPing The minimum time to delay sends.
703 	/// \param[in] extraPingVariance The additional random time to delay sends.
704     void ApplyNetworkSimulator( float packetloss, unsigned short minExtraPing, unsigned short extraPingVariance);
705 
706 	/// \brief Limits how much outgoing bandwidth can be used per-connection.
707 	/// This limit does not apply to the sum of all connections!
708 	/// Exceeding the limit queues up outgoing traffic.
709 	/// \param[in] maxBitsPerSecond Maximum bits per second to send.  Use 0 for unlimited (default). Once set, it takes effect immedately and persists until called again.
710 	void SetPerConnectionOutgoingBandwidthLimit( unsigned maxBitsPerSecond );
711 
712 	/// Returns true if you previously called ApplyNetworkSimulator.
713 	/// \return Ture if you previously called ApplyNetworkSimulator. False otherwise.
714 	bool IsNetworkSimulatorActive( void );
715 
716 	// --------------------------------------------------------------------------------------------Statistical Functions - Functions dealing with API performance--------------------------------------------------------------------------------------------
717 
718 	/// \brief Returns a structure containing a large set of network statistics for the specified system.
719 	/// You can map this data to a string using the C style StatisticsToString() function
720 	/// \param[in] systemAddress Which connected system to get statistics for.
721 	/// \param[in] rns If you supply this structure,the network statistics will be written to it. Otherwise the method uses a static struct to write the data, which is not threadsafe.
722 	/// \return 0 if the specified system can't be found. Otherwise a pointer to the struct containing the specified system's network statistics.
723 	/// \sa RakNetStatistics.h
724 	RakNetStatistics * const GetStatistics( const SystemAddress systemAddress, RakNetStatistics *rns=0 );
725 	/// \brief Returns the network statistics of the system at the given index in the remoteSystemList.
726 	///	\return True if the index is less than the maximum number of peers allowed and the system is active. False otherwise.
727 	bool GetStatistics( const int index, RakNetStatistics *rns );
728 
729 	/// \Returns how many messages are waiting when you call Receive()
730 	virtual unsigned int GetReceiveBufferSize(void);
731 
732 	// --------------------------------------------------------------------------------------------EVERYTHING AFTER THIS COMMENT IS FOR INTERNAL USE ONLY--------------------------------------------------------------------------------------------
733 	/// \internal
734 	char *GetRPCString( const char *data, const BitSize_t bitSize, const SystemAddress systemAddress);
735 
736 	/// \internal
737 	bool SendOutOfBand(const char *host, unsigned short remotePort, const char *data, BitSize_t dataLength, unsigned connectionSocketIndex=0 );
738 
739 	// static Packet *AllocPacket(unsigned dataSize, const char *file, unsigned int line);
740 
741 	/// \internal
742 	/// \brief Holds the clock differences between systems, along with the ping
743 	struct PingAndClockDifferential
744 	{
745 		unsigned short pingTime;
746 		RakNetTime clockDifferential;
747 	};
748 
749 	/// \internal
750 	/// \brief All the information representing a connected system system
751 	struct RemoteSystemStruct
752 	{
753 		bool isActive; // Is this structure in use?
754 		SystemAddress systemAddress;  /// Their external IP on the internet
755 		SystemAddress myExternalSystemAddress;  /// Your external IP on the internet, from their perspective
756 		SystemAddress theirInternalSystemAddress[MAXIMUM_NUMBER_OF_INTERNAL_IDS];  /// Their internal IP, behind the LAN
757 		ReliabilityLayer reliabilityLayer;  /// The reliability layer associated with this player
758 		bool weInitiatedTheConnection; /// True if we started this connection via Connect.  False if someone else connected to us.
759 		PingAndClockDifferential pingAndClockDifferential[ PING_TIMES_ARRAY_SIZE ];  /// last x ping times and calculated clock differentials with it
760 		int pingAndClockDifferentialWriteIndex;  /// The index we are writing into the pingAndClockDifferential circular buffer
761 		unsigned short lowestPing; ///The lowest ping value encountered
762 		RakNetTime nextPingTime;  /// When to next ping this player
763 		RakNetTime lastReliableSend; /// When did the last reliable send occur.  Reliable sends must occur at least once every timeoutTime/2 units to notice disconnects
764 		RakNetTime connectionTime; /// connection time, if active.
765 		unsigned char AESKey[ 16 ]; /// Security key.
766 		bool setAESKey; /// true if security is enabled.
767 //		int connectionSocketIndex; // index into connectionSockets to send back on.
768 		RPCMap rpcMap; /// Mapping of RPC calls to single byte integers to save transmission bandwidth.
769 		RakNetGUID guid;
770 		int MTUSize;
771 		// Reference counted socket to send back on
772 		RakNetSmartPtr<RakNetSocket> rakNetSocket;
773 
774 		enum ConnectMode {NO_ACTION, DISCONNECT_ASAP, DISCONNECT_ASAP_SILENTLY, DISCONNECT_ON_NO_ACK, REQUESTED_CONNECTION, HANDLING_CONNECTION_REQUEST, UNVERIFIED_SENDER, SET_ENCRYPTION_ON_MULTIPLE_16_BYTE_PACKET, CONNECTED} connectMode;
775 	};
776 
777 protected:
778 
779 	friend RAK_THREAD_DECLARATION(UpdateNetworkLoop);
780 	friend RAK_THREAD_DECLARATION(RecvFromLoop);
781 	friend RAK_THREAD_DECLARATION(UDTConnect);
782 
783 	/*
784 #ifdef _WIN32
785 	// friend unsigned __stdcall RecvFromNetworkLoop(LPVOID arguments);
786 	friend void __stdcall ProcessPortUnreachable( const unsigned int binaryAddress, const unsigned short port, RakPeer *rakPeer );
787 	friend void __stdcall ProcessNetworkPacket( const unsigned int binaryAddress, const unsigned short port, const char *data, const int length, RakPeer *rakPeer, unsigned connectionSocketIndex );
788 	friend unsigned __stdcall UpdateNetworkLoop( LPVOID arguments );
789 #else
790 	// friend void*  RecvFromNetworkLoop( void*  arguments );
791 	friend void ProcessPortUnreachable( const unsigned int binaryAddress, const unsigned short port, RakPeer *rakPeer );
792 	friend void ProcessNetworkPacket( const unsigned int binaryAddress, const unsigned short port, const char *data, const int length, RakPeer *rakPeer, unsigned connectionSocketIndex );
793 	friend void* UpdateNetworkLoop( void* arguments );
794 #endif
795 	*/
796 
797 	friend void ProcessPortUnreachable( const unsigned int binaryAddress, const unsigned short port, RakPeer *rakPeer );
798 	friend bool ProcessOfflineNetworkPacket( const SystemAddress systemAddress, const char *data, const int length, RakPeer *rakPeer, RakNetSmartPtr<RakNetSocket> rakNetSocket, bool *isOfflineMessage, RakNetTimeUS timeRead );
799 	friend void ProcessNetworkPacket( const SystemAddress systemAddress, const char *data, const int length, RakPeer *rakPeer, RakNetSmartPtr<RakNetSocket> rakNetSocket, RakNetTimeUS timeRead );
800 	friend void ProcessNetworkPacket( const SystemAddress systemAddress, const char *data, const int length, RakPeer *rakPeer, RakNetTimeUS timeRead );
801 
802 	// This is done to provide custom RPC handling when in a blocking RPC
803 	Packet* ReceiveIgnoreRPC( void );
804 
805 	int GetIndexFromSystemAddress( const SystemAddress systemAddress, bool calledFromNetworkThread ) const;
806 	int GetIndexFromGuid( const RakNetGUID guid );
807 
808 	//void RemoveFromRequestedConnectionsList( const SystemAddress systemAddress );
809 	// Two versions needed because some buggy compilers strip the last parameter if unused, and crashes
810 	bool SendConnectionRequest( const char* host, unsigned short remotePort, const char *passwordData, int passwordDataLength, unsigned connectionSocketIndex, unsigned int extraData, unsigned sendConnectionAttemptCount, unsigned timeBetweenSendConnectionAttemptsMS, RakNetTime timeoutTime, RakNetSmartPtr<RakNetSocket> socket );
811 	bool SendConnectionRequest( const char* host, unsigned short remotePort, const char *passwordData, int passwordDataLength, unsigned connectionSocketIndex, unsigned int extraData, unsigned sendConnectionAttemptCount, unsigned timeBetweenSendConnectionAttemptsMS, RakNetTime timeoutTime );
812 	///Get the reliability layer associated with a systemAddress.
813 	/// \param[in] systemAddress The player identifier
814 	/// \return 0 if none
815 	RemoteSystemStruct *GetRemoteSystemFromSystemAddress( const SystemAddress systemAddress, bool calledFromNetworkThread, bool onlyActive ) const;
816 	RakPeer::RemoteSystemStruct *GetRemoteSystem( const AddressOrGUID systemIdentifier, bool calledFromNetworkThread, bool onlyActive ) const;
817 	void ValidateRemoteSystemLookup(void) const;
818 	RemoteSystemStruct *GetRemoteSystemFromGUID( const RakNetGUID guid, bool onlyActive ) const;
819 	///Parse out a connection request packet
820 	void ParseConnectionRequestPacket( RakPeer::RemoteSystemStruct *remoteSystem, SystemAddress systemAddress, const char *data, int byteSize);
821 	///When we get a connection request from an ip / port, accept it unless full
822 	void OnConnectionRequest( RakPeer::RemoteSystemStruct *remoteSystem, unsigned char *AESKey, bool setAESKey, RakNetTime incomingTimestamp );
823 	void SendConnectionRequestAccepted(RakPeer::RemoteSystemStruct *remoteSystem, RakNetTime incomingTimestamp);
824 	///Send a reliable disconnect packet to this player and disconnect them when it is delivered
825 	void NotifyAndFlagForShutdown( const SystemAddress systemAddress, bool performImmediate, unsigned char orderingChannel, PacketPriority disconnectionNotificationPriority );
826 	///Returns how many remote systems initiated a connection to us
827 	unsigned short GetNumberOfRemoteInitiatedConnections( void ) const;
828 	///	\brief Get a free remote system from the list and assign our systemAddress to it.
829 	/// \note Should only be called from the update thread - not the user thread.
830 	/// \param[in] systemAddress	systemAddress to be assigned
831 	/// \param[in] connectionMode	connection mode of the RemoteSystem.
832 	/// \param[in] rakNetSocket
833 	/// \param[in] thisIPConnectedRecently	Is this IP connected recently? set to False;
834 	/// \param[in] bindingAddress	Address to be binded with the remote system
835 	/// \param[in] incomingMTU	MTU for the remote system
836 	RemoteSystemStruct * AssignSystemAddressToRemoteSystemList( const SystemAddress systemAddress, RemoteSystemStruct::ConnectMode connectionMode, RakNetSmartPtr<RakNetSocket> incomingRakNetSocket, bool *thisIPConnectedRecently, SystemAddress bindingAddress, int incomingMTU, RakNetGUID guid );
837 	///	\brief Adjust the timestamp of the incoming packet to be relative to this system.
838 	/// \param[in] data	Data in the incoming packet.
839 	/// \param[in] systemAddress Sender of the incoming packet.
840 	void ShiftIncomingTimestamp( unsigned char *data, SystemAddress systemAddress ) const;
841 	/// Get the most accurate clock differential for a certain player.
842 	/// \param[in] systemAddress The player with whose clock the time difference is calculated.
843 	/// \returns The clock differential for a certain player.
844 	RakNetTime GetBestClockDifferential( const SystemAddress systemAddress ) const;
845 
846 	//void PushPortRefused( const SystemAddress target );
847 	///  \brief Handles an RPC packet.  This packet has an RPC request
848 	/// \param[in] data A packet returned from Receive with the ID ID_RPC
849 	/// \param[in] length The size of the packet data
850 	/// \param[in] systemAddress The sender of the packet
851 	/// \return True on success, false on a bad packet or an unregistered function
852 	bool HandleRPCPacket( const char *data, int length, SystemAddress systemAddress );
853 
854 	///	\brief Handles an RPC reply packet.  The reply packet has data returned from an RPC call
855 	/// \param[in] data A packet returned from Receive with the ID ID_RPC
856 	/// \param[in] length The size of the packet data
857 	/// \param[in] systemAddress The sender of the packet
858 	void HandleRPCReplyPacket( const char *data, int length, SystemAddress systemAddress );
859 
860 	bool IsLoopbackAddress(const AddressOrGUID &systemIdentifier, bool matchPort) const;
861 	SystemAddress GetLoopbackAddress(void) const;
862 
863 	///Set this to true to terminate the Peer thread execution
864 	volatile bool endThreads;
865 	///true if the peer thread is active.
866 	volatile bool isMainLoopThreadActive,isRecvFromLoopThreadActive;
867 	bool occasionalPing;  /// Do we occasionally ping the other systems?*/
868 	///Store the maximum number of peers allowed to connect
869 	unsigned short maximumNumberOfPeers;
870 	//05/02/06 Just using maximumNumberOfPeers instead
871 	///Store the maximum number of peers able to connect, including reserved connection slots for pings, etc.
872 	//unsigned short remoteSystemListSize;
873 	///Store the maximum incoming connection allowed
874 	unsigned short maximumIncomingConnections;
875 	RakNet::BitStream offlinePingResponse;
876 	///Local Player ID
877 	SystemAddress mySystemAddress[MAXIMUM_NUMBER_OF_INTERNAL_IDS];
878 	char incomingPassword[256];
879 	unsigned char incomingPasswordLength;
880 
881 	/// This is an array of pointers to RemoteSystemStruct
882 	/// This allows us to preallocate the list when starting, so we don't have to allocate or delete at runtime.
883 	/// Another benefit is that is lets us add and remove active players simply by setting systemAddress
884 	/// and moving elements in the list by copying pointers variables without affecting running threads, even if they are in the reliability layer
885 	RemoteSystemStruct* remoteSystemList;
886 
887 	// Use a hash, with binaryAddress plus port mod length as the index
888 	RemoteSystemIndex **remoteSystemLookup;
889 	unsigned int RemoteSystemLookupHashIndex(SystemAddress sa) const;
890 	void ReferenceRemoteSystem(SystemAddress sa, unsigned int remoteSystemListIndex);
891 	void DereferenceRemoteSystem(SystemAddress sa);
892 	RemoteSystemStruct* GetRemoteSystem(SystemAddress sa) const;
893 	unsigned int GetRemoteSystemIndex(SystemAddress sa) const;
894 	void ClearRemoteSystemLookup(void);
895 	DataStructures::MemoryPool<RemoteSystemIndex> remoteSystemIndexPool;
896 
897 //	unsigned int LookupIndexUsingHashIndex(SystemAddress sa) const;
898 //	unsigned int RemoteSystemListIndexUsingHashIndex(SystemAddress sa) const;
899 //	unsigned int FirstFreeRemoteSystemLookupIndex(SystemAddress sa) const;
900 
901 	enum
902 	{
903 		// Only put these mutexes in user thread functions!
904 #ifdef _RAKNET_THREADSAFE
905 		requestedConnectionList_Mutex,
906 #endif
907 		offlinePingResponse_Mutex,
908 		NUMBER_OF_RAKPEER_MUTEXES
909 	};
910 	SimpleMutex rakPeerMutexes[ NUMBER_OF_RAKPEER_MUTEXES ];
911 	///RunUpdateCycle is not thread safe but we don't need to mutex calls. Just skip calls if it is running already
912 
913 	bool updateCycleIsRunning;
914 	///The list of people we have tried to connect to recently
915 
916 	//DataStructures::Queue<RequestedConnectionStruct*> requestedConnectionsList;
917 	///Data that both the client and the server needs
918 
919 	unsigned int bytesSentPerSecond, bytesReceivedPerSecond;
920 	// bool isSocketLayerBlocking;
921 	// bool continualPing,isRecvfromThreadActive,isMainLoopThreadActive, endThreads, isSocketLayerBlocking;
922 	unsigned int validationInteger;
923 	SimpleMutex incomingQueueMutex, banListMutex; //,synchronizedMemoryQueueMutex, automaticVariableSynchronizationMutex;
924 	//DataStructures::Queue<Packet *> incomingpacketSingleProducerConsumer; //, synchronizedMemorypacketSingleProducerConsumer;
925 	// BitStream enumerationData;
926 
927 	struct BanStruct
928 	{
929 		char *IP;
930 		RakNetTime timeout; // 0 for none
931 	};
932 
933 	struct RequestedConnectionStruct
934 	{
935 		SystemAddress systemAddress;
936 		RakNetTime nextRequestTime;
937 		unsigned char requestsMade;
938 		char *data;
939 		unsigned short dataLength;
940 		char outgoingPassword[256];
941 		unsigned char outgoingPasswordLength;
942 		unsigned socketIndex;
943 		unsigned int extraData;
944 		unsigned sendConnectionAttemptCount;
945 		unsigned timeBetweenSendConnectionAttemptsMS;
946 		RakNetTime timeoutTime;
947 		RakNetSmartPtr<RakNetSocket> socket;
948 		enum {CONNECT=1, /*PING=2, PING_OPEN_CONNECTIONS=4,*/ /*ADVERTISE_SYSTEM=2*/} actionToTake;
949 	};
950 
951 	//DataStructures::List<DataStructures::List<MemoryBlock>* > automaticVariableSynchronizationList;
952 	DataStructures::List<BanStruct*> banList;
953 	DataStructures::List<PluginInterface2*> messageHandlerList;
954 
955 	DataStructures::Queue<RequestedConnectionStruct*> requestedConnectionQueue;
956 	SimpleMutex requestedConnectionQueueMutex;
957 
958 	/// Compression stuff
959 	unsigned int frequencyTable[ 256 ];
960 	HuffmanEncodingTree *inputTree, *outputTree;
961 	unsigned int rawBytesSent, rawBytesReceived, compressedBytesSent, compressedBytesReceived;
962 	// void DecompressInput(RakNet::BitStream *bitStream);
963 	// void UpdateOutgoingFrequencyTable(RakNet::BitStream * bitStream);
964 	void GenerateSYNCookieRandomNumber( void );
965 	void SecuredConnectionResponse( const SystemAddress systemAddress );
966 	void SecuredConnectionConfirmation( RakPeer::RemoteSystemStruct * remoteSystem, char* data );
967 	bool RunUpdateCycle( RakNetTimeUS timeNS, RakNetTime timeMS );
968 	// void RunMutexedUpdateCycle(void);
969 
970 	struct BufferedCommandStruct
971 	{
972 		BitSize_t numberOfBitsToSend;
973 		PacketPriority priority;
974 		PacketReliability reliability;
975 		char orderingChannel;
976 		AddressOrGUID systemIdentifier;
977 		bool broadcast;
978 		RemoteSystemStruct::ConnectMode connectionMode;
979 		NetworkID networkID;
980 		bool blockingCommand; // Only used for RPC
981 		char *data;
982 		bool haveRakNetCloseSocket;
983 		unsigned connectionSocketIndex;
984 		unsigned short remotePortRakNetWasStartedOn_PS3;
985 		SOCKET socket;
986 		unsigned short port;
987 		uint32_t receipt;
988 		enum {BCS_SEND, BCS_CLOSE_CONNECTION, BCS_GET_SOCKET, BCS_CHANGE_SYSTEM_ADDRESS,/* BCS_USE_USER_SOCKET, BCS_REBIND_SOCKET_ADDRESS, BCS_RPC, BCS_RPC_SHIFT,*/BCS_SEND_OUT_OF_BAND, BCS_DO_NOTHING} command;
989 	};
990 
991 	// Single producer single consumer queue using a linked list
992 	//BufferedCommandStruct* bufferedCommandReadIndex, bufferedCommandWriteIndex;
993 
994 #ifndef _RAKNET_THREADSAFE
995 	DataStructures::SingleProducerConsumer<BufferedCommandStruct> bufferedCommands;
996 #else
997 	DataStructures::ThreadsafeAllocatingQueue<BufferedCommandStruct> bufferedCommands;
998 #endif
999 
1000 	// Constructor not called!
1001 	struct RecvFromStruct
1002 	{
1003 
1004 
1005 
1006 		char data[MAXIMUM_MTU_SIZE];
1007 
1008 		int bytesRead;
1009 		SystemAddress systemAddress;
1010 		RakNetTimeUS timeRead;
1011 		SOCKET s;
1012 		unsigned short remotePortRakNetWasStartedOn_PS3;
1013 	};
1014 
1015 #ifndef _RAKNET_THREADSAFE
1016 	DataStructures::SingleProducerConsumer<RecvFromStruct> bufferedPackets;
1017 #else
1018 	DataStructures::ThreadsafeAllocatingQueue<RecvFromStruct> bufferedPackets;
1019 #endif
1020 
1021 	struct SocketQueryOutput
1022 	{
SocketQueryOutputSocketQueryOutput1023 		SocketQueryOutput() {}
~SocketQueryOutputSocketQueryOutput1024 		~SocketQueryOutput() {}
1025 		DataStructures::List<RakNetSmartPtr<RakNetSocket> > sockets;
1026 	};
1027 #ifndef _RAKNET_THREADSAFE
1028 	DataStructures::SingleProducerConsumer< SocketQueryOutput > socketQueryOutput;
1029 #else
1030 	DataStructures::ThreadsafeAllocatingQueue<SocketQueryOutput> socketQueryOutput;
1031 #endif
1032 
1033 	bool AllowIncomingConnections(void) const;
1034 
1035 	void PingInternal( const SystemAddress target, bool performImmediate, PacketReliability reliability );
1036 	bool ValidSendTarget(SystemAddress systemAddress, bool broadcast);
1037 	// This stores the user send calls to be handled by the update thread.  This way we don't have thread contention over systemAddresss
1038 	void CloseConnectionInternal( const AddressOrGUID& systemIdentifier, bool sendDisconnectionNotification, bool performImmediate, unsigned char orderingChannel, PacketPriority disconnectionNotificationPriority );
1039 	void SendBuffered( const char *data, BitSize_t numberOfBitsToSend, PacketPriority priority, PacketReliability reliability, char orderingChannel, const AddressOrGUID systemIdentifier, bool broadcast, RemoteSystemStruct::ConnectMode connectionMode, uint32_t receipt );
1040 	void SendBufferedList( const char **data, const int *lengths, const int numParameters, PacketPriority priority, PacketReliability reliability, char orderingChannel, const AddressOrGUID systemIdentifier, bool broadcast, RemoteSystemStruct::ConnectMode connectionMode, uint32_t receipt );
1041 	bool SendImmediate( char *data, BitSize_t numberOfBitsToSend, PacketPriority priority, PacketReliability reliability, char orderingChannel, const AddressOrGUID systemIdentifier, bool broadcast, bool useCallerDataAllocation, RakNetTimeUS currentTime, uint32_t receipt );
1042 	//bool HandleBufferedRPC(BufferedCommandStruct *bcs, RakNetTime time);
1043 	void ClearBufferedCommands(void);
1044 	void ClearBufferedPackets(void);
1045 	void ClearSocketQueryOutput(void);
1046 	void ClearRequestedConnectionList(void);
1047 	void AddPacketToProducer(Packet *p);
1048 	unsigned int GenerateSeedFromGuid(void);
1049 	SimpleMutex securityExceptionMutex;
1050 
1051 	//DataStructures::AVLBalancedBinarySearchTree<RPCNode> rpcTree;
1052 	RPCMap rpcMap; // Can't use StrPtrHash because runtime insertions will screw up the indices
1053 	int defaultMTUSize;
1054 	bool trackFrequencyTable;
1055 	int threadSleepTimer;
1056 
1057 	// Smart pointer so I can return the object to the user
1058 	DataStructures::List<RakNetSmartPtr<RakNetSocket> > socketList;
1059 	void DerefAllSockets(void);
1060 	unsigned int GetRakNetSocketFromUserConnectionSocketIndex(unsigned int userIndex) const;
1061 	// Used for RPC replies
1062 	RakNet::BitStream *replyFromTargetBS;
1063 	SystemAddress replyFromTargetPlayer;
1064 	bool replyFromTargetBroadcast;
1065 
1066 	RakNetTime defaultTimeoutTime;
1067 
1068 	// Problem:
1069 	// Waiting in function A:
1070 	// Wait function gets RPC B:
1071 	//
1072 	bool blockOnRPCReply;
1073 
1074 	// For redirecting sends through the router plugin.  Unfortunate I have to use this architecture.
1075 	RouterInterface *router;
1076 
1077 	// Generate and store a unique GUID
1078 	void GenerateGUID(void);
1079 	unsigned int GetSystemIndexFromGuid( const RakNetGUID input ) const;
1080 	RakNetGUID myGuid;
1081 
1082 	unsigned maxOutgoingBPS;
1083 
1084 	// Nobody would use the internet simulator in a final build.
1085 #ifdef _DEBUG
1086 	double _packetloss;
1087 	unsigned short _minExtraPing, _extraPingVariance;
1088 #endif
1089 
1090 #if   !defined(_WIN32_WCE)
1091 	/// Encryption and security
1092 	RSACrypt rsacrypt;
1093 	uint32_t publicKeyE;
1094 	uint32_t publicKeyN[RAKNET_RSA_FACTOR_LIMBS];
1095 	bool keysLocallyGenerated, usingSecurity;
1096 	RakNetTime randomNumberExpirationTime;
1097 	unsigned char newRandomNumber[ 20 ], oldRandomNumber[ 20 ];
1098 
1099 
1100 	/*
1101 	big::RSACrypt<RSA_BIT_SIZE> rsacrypt;
1102 	big::u32 publicKeyE;
1103 	RSA_BIT_SIZE publicKeyN;
1104 	bool keysLocallyGenerated, usingSecurity;
1105 	RakNetTime randomNumberExpirationTime;
1106 	unsigned char newRandomNumber[ 20 ], oldRandomNumber[ 20 ];
1107 	*/
1108 #endif
1109 
1110 	///How long it has been since things were updated by a call to receiveUpdate thread uses this to determine how long to sleep for
1111 	//unsigned int lastUserUpdateCycle;
1112 	/// True to allow connection accepted packets from anyone.  False to only allow these packets from servers we requested a connection to.
1113 	bool allowConnectionResponseIPMigration;
1114 
1115 	SystemAddress firstExternalID;
1116 	int splitMessageProgressInterval;
1117 	RakNetTime unreliableTimeout;
1118 
1119 
1120 	// Used for object lookup for RPC (actually deprecated, since RPC is deprecated)
1121 	NetworkIDManager *networkIDManager;
1122 	// Systems in this list will not go through the secure connection process, even when secure connections are turned on. Wildcards are accepted.
1123 	DataStructures::List<RakNet::RakString> securityExceptionList;
1124 
1125 	char ipList[ MAXIMUM_NUMBER_OF_INTERNAL_IDS ][ 16 ];
1126 	unsigned int binaryAddresses[MAXIMUM_NUMBER_OF_INTERNAL_IDS];
1127 
1128 	bool allowInternalRouting;
1129 
1130 	void (*userUpdateThreadPtr)(RakPeerInterface *, void *);
1131 	void *userUpdateThreadData;
1132 
1133 
1134 	SignaledEvent quitAndDataEvents;
1135 	bool limitConnectionFrequencyFromTheSameIP;
1136 
1137 	SimpleMutex packetAllocationPoolMutex;
1138 	DataStructures::MemoryPool<Packet> packetAllocationPool;
1139 
1140 	SimpleMutex packetReturnMutex;
1141 	DataStructures::Queue<Packet*> packetReturnQueue;
1142 	Packet *AllocPacket(unsigned dataSize, const char *file, unsigned int line);
1143 	Packet *AllocPacket(unsigned dataSize, unsigned char *data, const char *file, unsigned int line);
1144 
1145 	/// This is used to return a number to the user when they call Send identifying the message
1146 	/// This number will be returned back with ID_SND_RECEIPT_ACKED or ID_SND_RECEIPT_LOSS and is only returned
1147 	/// with the reliability types that contain RECEIPT in the name
1148 	SimpleMutex sendReceiptSerialMutex;
1149 	uint32_t sendReceiptSerial;
1150 	void ResetSendReceipt(void);
1151 
1152 	void OnConnectedPong(RakNetTime sendPingTime, RakNetTime sendPongTime, RemoteSystemStruct *remoteSystem);
1153 };
1154 
1155 #endif
1156