Shadowrun: Awakened 29 September 2011 - Build 871
TCPInterface.h
Go to the documentation of this file.
00001 
00002 
00003 
00004 
00005 
00006 
00007 
00008 #include "NativeFeatureIncludes.h"
00009 #if _RAKNET_SUPPORT_TCPInterface==1
00010 
00011 #ifndef __SIMPLE_TCP_SERVER
00012 #define __SIMPLE_TCP_SERVER
00013 
00014 #include "RakMemoryOverride.h"
00015 #include "DS_List.h"
00016 #include "RakNetTypes.h"
00017 #include "Export.h"
00018 #include "RakThread.h"
00019 #include "DS_Queue.h"
00020 #include "SimpleMutex.h"
00021 #include "RakNetDefines.h"
00022 #include "SocketIncludes.h"
00023 #include "DS_ByteQueue.h"
00024 #include "DS_ThreadsafeAllocatingQueue.h"
00025 
00026 #if OPEN_SSL_CLIENT_SUPPORT==1
00027 #include <openssl/crypto.h>
00028 #include <openssl/x509.h>
00029 #include <openssl/pem.h>
00030 #include <openssl/ssl.h>
00031 #include <openssl/err.h>
00032 #endif
00033 
00034 namespace RakNet
00035 {
00037 struct RemoteClient;
00038 
00041 class RAK_DLL_EXPORT TCPInterface
00042 {
00043 public:
00044     // GetInstance() and DestroyInstance(instance*)
00045     STATIC_FACTORY_DECLARATIONS(TCPInterface)
00046 
00047     TCPInterface();
00048     virtual ~TCPInterface();
00049 
00056     bool Start(unsigned short port, unsigned short maxIncomingConnections, unsigned short maxConnections=0, int _threadPriority=-99999, unsigned short socketFamily=AF_INET);
00057 
00059     void Stop(void);
00060 
00062     SystemAddress Connect(const char* host, unsigned short remotePort, bool block=true, unsigned short socketFamily=AF_INET);
00063 
00064 #if OPEN_SSL_CLIENT_SUPPORT==1
00065 
00066     void StartSSLClient(SystemAddress systemAddress);
00067 
00069     bool IsSSLActive(SystemAddress systemAddress);
00070 #endif
00071 
00073     void Send( const char *data, unsigned int length, const SystemAddress &systemAddress, bool broadcast );
00074 
00075     // Sends a concatenated list of byte streams
00076     bool SendList( const char **data, const unsigned int  *lengths, const int numParameters, const SystemAddress &systemAddress, bool broadcast );
00077 
00078     // Get how many bytes are waiting to be sent. If too many, you may want to skip sending
00079     unsigned int GetOutgoingDataBufferSize(SystemAddress systemAddress) const;
00080 
00082     bool ReceiveHasPackets( void );
00083 
00085     Packet* Receive( void );
00086 
00088     void CloseConnection( SystemAddress systemAddress );
00089 
00091     void DeallocatePacket( Packet *packet );
00092 
00096     void GetConnectionList( SystemAddress *remoteSystems, unsigned short *numberOfSystems ) const;
00097 
00099     unsigned short GetConnectionCount(void) const;
00100 
00103     SystemAddress HasCompletedConnectionAttempt(void);
00104 
00107     SystemAddress HasFailedConnectionAttempt(void);
00108 
00110     SystemAddress HasNewIncomingConnection(void);
00111 
00113     SystemAddress HasLostConnection(void);
00114 
00116     Packet* AllocatePacket(unsigned dataSize);
00117 
00118     // Push a packet back to the queue
00119     virtual void PushBackPacket( Packet *packet, bool pushAtHead );
00120 
00121     static const char *Base64Map(void) {return "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/";}
00122 
00124     static int Base64Encoding(const char *inputData, int dataLength, char *outputData);
00125 
00127     bool WasStarted(void) const;
00128 
00129 protected:
00130 
00131     bool isStarted, threadRunning;
00132     SOCKET listenSocket;
00133 
00134     DataStructures::Queue<Packet*> headPush, tailPush;
00135     RemoteClient* remoteClients;
00136     int remoteClientsLength;
00137 
00138     // Assuming remoteClients is only used by one thread!
00139     // DataStructures::List<RemoteClient*> remoteClients;
00140     // Use this thread-safe queue to add to remoteClients
00141     // DataStructures::Queue<RemoteClient*> remoteClientsInsertionQueue;
00142     // SimpleMutex remoteClientsInsertionQueueMutex;
00143 
00144     /*
00145     struct OutgoingMessage
00146     {
00147         unsigned char* data;
00148         SystemAddress systemAddress;
00149         bool broadcast;
00150         unsigned int length;
00151     };
00152     */
00153 //  DataStructures::SingleProducerConsumer<OutgoingMessage> outgoingMessages;
00154 //  DataStructures::SingleProducerConsumer<Packet> incomingMessages;
00155 //  DataStructures::SingleProducerConsumer<SystemAddress> newIncomingConnections, lostConnections, requestedCloseConnections;
00156 //  DataStructures::SingleProducerConsumer<RemoteClient*> newRemoteClients;
00157 //  DataStructures::ThreadsafeAllocatingQueue<OutgoingMessage> outgoingMessages;
00158     DataStructures::ThreadsafeAllocatingQueue<Packet> incomingMessages;
00159     DataStructures::ThreadsafeAllocatingQueue<SystemAddress> newIncomingConnections, lostConnections, requestedCloseConnections;
00160     DataStructures::ThreadsafeAllocatingQueue<RemoteClient*> newRemoteClients;
00161     SimpleMutex completedConnectionAttemptMutex, failedConnectionAttemptMutex;
00162     DataStructures::Queue<SystemAddress> completedConnectionAttempts, failedConnectionAttempts;
00163 
00164     int threadPriority;
00165 
00166     DataStructures::List<SOCKET> blockingSocketList;
00167     SimpleMutex blockingSocketListMutex;
00168 
00169 
00170 
00171 
00172 
00173     friend RAK_THREAD_DECLARATION(UpdateTCPInterfaceLoop);
00174     friend RAK_THREAD_DECLARATION(ConnectionAttemptLoop);
00175 
00176 //  void DeleteRemoteClient(RemoteClient *remoteClient, fd_set *exceptionFD);
00177 //  void InsertRemoteClient(RemoteClient* remoteClient);
00178     SOCKET SocketConnect(const char* host, unsigned short remotePort, unsigned short socketFamily);
00179 
00180     struct ThisPtrPlusSysAddr
00181     {
00182         TCPInterface *tcpInterface;
00183         SystemAddress systemAddress;
00184         bool useSSL;
00185         unsigned short socketFamily;
00186     };
00187 
00188 #if OPEN_SSL_CLIENT_SUPPORT==1
00189     SSL_CTX* ctx;
00190     SSL_METHOD *meth;
00191     DataStructures::ThreadsafeAllocatingQueue<SystemAddress> startSSL;
00192     DataStructures::List<SystemAddress> activeSSLConnections;
00193     SimpleMutex sharedSslMutex;
00194 #endif
00195 };
00196 
00198 struct RemoteClient
00199 {
00200     RemoteClient() {
00201 #if OPEN_SSL_CLIENT_SUPPORT==1
00202         ssl=0;
00203 #endif
00204         isActive=false;
00205         socket=INVALID_SOCKET;
00206     }
00207     SOCKET socket;
00208     SystemAddress systemAddress;
00209     DataStructures::ByteQueue outgoingData;
00210     bool isActive;
00211     SimpleMutex outgoingDataMutex;
00212     SimpleMutex isActiveMutex;
00213 
00214 #if OPEN_SSL_CLIENT_SUPPORT==1
00215     SSL*     ssl;
00216     void InitSSL(SSL_CTX* ctx, SSL_METHOD *meth);
00217     void DisconnectSSL(void);
00218     void FreeSSL(void);
00219     int Send(const char *data, unsigned int length);
00220     int Recv(char *data, const int dataSize);
00221 #else
00222     int Send(const char *data, unsigned int length);
00223     int Recv(char *data, const int dataSize);
00224 #endif
00225     void Reset(void)
00226     {
00227         outgoingDataMutex.Lock();
00228         outgoingData.Clear(_FILE_AND_LINE_);
00229         outgoingDataMutex.Unlock();
00230     }
00231     void SetActive(bool a);
00232     void SendOrBuffer(const char **data, const unsigned int *lengths, const int numParameters);
00233 };
00234 
00235 } // namespace RakNet
00236 
00237 #endif
00238 
00239 #endif // _RAKNET_SUPPORT_*
00240 

Copyright © 2007-2010 by The Shadowrun: Awakened Team. This work is licensed under the GNU Lesser General Public License 3.

GNU Lesser General Public License 3 Sourceforge.net