Restructured src folder to be more clean

This commit is contained in:
seefo
2018-01-11 04:17:47 -05:00
parent e99d0f02a8
commit 3e3d18d318
20987 changed files with 5 additions and 1940589 deletions
@@ -0,0 +1,272 @@
#include "GenericApiCore.h"
#include "GenericConnection.h"
#include "GenericMessage.h"
//----------------------------------------
//
// WARNING: These files are NOT standard generic API files
// They have been modified for this project.
// Do NOT replace them with generic API files
//
//----------------------------------------
using namespace std;
#ifdef EXTERNAL_DISTRO
namespace NAMESPACE
{
#endif
//----------------------------------------
ServerTrackObject::ServerTrackObject(unsigned mapped_track, unsigned real_track, GenericConnection *con)
: m_mappedTrack(mapped_track), m_realTrack(real_track), m_connection(con)
//----------------------------------------
{
}
//----------------------------------------
GenericAPICore::GenericAPICore(const char *host,
short port,
unsigned reqTimeout,
unsigned reconnectTimeout,
unsigned noDataTimeoutSecs,
unsigned noAckTimeoutSecs,
unsigned incomingBufSizeInKB,
unsigned outgoingBufSizeInKB,
unsigned keepAlive,
unsigned maxRecvMessageSizeInKB)
: m_currTrack(0),
m_reconnectTimeout(0),
m_outCount(0),
m_pendingCount(0),
m_requestTimeout(reqTimeout),
m_currentConnections(0), m_maxConnections(0),
m_suspended(false),
m_nextConnectionIndex(0)
//----------------------------------------
{
GenericConnection *con = new GenericConnection(host, port, this, reconnectTimeout, noDataTimeoutSecs, noAckTimeoutSecs, incomingBufSizeInKB, outgoingBufSizeInKB, keepAlive, maxRecvMessageSizeInKB);
m_serverConnections.push_back(con);
}
//----------------------------------------
GenericAPICore::GenericAPICore(const char *game, const char *hosts[],
const short port[],
unsigned arraySize,
unsigned reqTimeout,
unsigned reconnectTimeout,
unsigned noDataTimeoutSecs,
unsigned noAckTimeoutSecs,
unsigned incomingBufSizeInKB,
unsigned outgoingBufSizeInKB,
unsigned keepAlive,
unsigned maxRecvMessageSizeInKB)
: m_currTrack(0),
m_reconnectTimeout(0),
m_outCount(0),
m_pendingCount(0),
m_requestTimeout(reqTimeout),
m_currentConnections(0), m_maxConnections(0),
m_suspended(false),
m_nextConnectionIndex(0),
m_game(game)
//----------------------------------------
{
for (unsigned i=0; i<arraySize; i++)
{
GenericConnection *con = new GenericConnection(hosts[i], port[i], this, reconnectTimeout, noDataTimeoutSecs, noAckTimeoutSecs, incomingBufSizeInKB, outgoingBufSizeInKB, keepAlive, maxRecvMessageSizeInKB);
m_serverConnections.push_back(con);
}
}
//----------------------------------------
GenericAPICore::~GenericAPICore()
//----------------------------------------
{
for (std::vector<GenericConnection *>::iterator conIter = m_serverConnections.begin(); conIter != m_serverConnections.end(); conIter++)
{
GenericConnection *con = *conIter;
delete con;
}
m_serverConnections.clear();
for(map<unsigned, GenericResponse *>::iterator iter = m_pending.begin(); iter != m_pending.end(); ++iter)
{
delete (*iter).second;
}
m_pending.empty();
while(m_outCount > 0)
{
delete m_outboundQueue.front().second;
delete m_outboundQueue.front().first;
m_outboundQueue.pop();
--m_outCount;
}
}
//----------------------------------------
unsigned GenericAPICore::submitRequest(GenericRequest *req, GenericResponse *res)
//----------------------------------------
{
++m_outCount;
if(m_currTrack == 0)
{
m_currTrack++;
}
req->setTrack(m_currTrack);
res->setTrack(m_currTrack);
time_t timeout = time(NULL) + m_requestTimeout;
req->setTimeout(timeout);
res->setTimeout(timeout);
m_outboundQueue.push(pair<GenericRequest *, GenericResponse *>(req, res));
return(m_currTrack++);
}
//----------------------------------------
void GenericAPICore::process()
//----------------------------------------
{
GenericRequest *req;
GenericResponse *res;
if (!m_suspended)
{
// Process timeout on pending requests
while((m_outCount > 0) && ((req = m_outboundQueue.front().first)->getTimeout() <= time(NULL)))
{
--m_outCount;
res = m_outboundQueue.front().second;
m_outboundQueue.pop();
responseCallback(res);
delete res;
delete req;
}
// Process timeout on pending responses
while((m_pendingCount > 0) && ((res = (*m_pending.begin()).second)->getTimeout() <= time(NULL)))
{
--m_pendingCount;
m_pending.erase(m_pending.begin());
responseCallback(res);
delete res;
}
while(m_outCount > 0)
{
pair<GenericRequest *, GenericResponse *> out_pair = m_outboundQueue.front();
req = out_pair.first;
res = out_pair.second;
GenericConnection *con = NULL;
if (req->getMappedServerTrack() == 0) // request has no originating "owner" server
{
con = getNextActiveConnection(); // it does not matter which server we send this to
}
else
{
ServerTrackObject *stobj = findServer(req->getMappedServerTrack());
if (stobj)
{
con = stobj->getConnection(); // the server connection to respond to
req->setServerTrack(stobj->getRealServerTrack()); // map server track back to REAL server track
//printf("\nUnmapping %d to %d", stobj->getMappedServerTrack(), req->getMappedServerTrack()); //debug
delete stobj;
}
}
if (con != NULL)
{
Base::ByteStream msg;
req->pack(msg);
con->Send(msg);
m_pending.insert(pair<unsigned, GenericResponse *>(res->getTrack(), res));
--m_outCount;
++m_pendingCount;
m_outboundQueue.pop();
delete req;
}
else
{
//no active connections
break; //from while loop
}
}
}
for (std::vector<GenericConnection *>::iterator conIter = m_serverConnections.begin(); conIter != m_serverConnections.end(); conIter++)
{
GenericConnection *con = *conIter;
con->process();
}
}
//----------------------------------------
GenericConnection *GenericAPICore::getNextActiveConnection()
//----------------------------------------
{
unsigned startIndex = m_nextConnectionIndex;
unsigned maxIndex = m_serverConnections.size() - 1;
GenericConnection *con = NULL;
//loop until we find an active connection, or until we get back
// to where we started
do
{
if (m_serverConnections[m_nextConnectionIndex]->isConnected())
{
con = m_serverConnections[m_nextConnectionIndex];
if (m_nextConnectionIndex == maxIndex)
m_nextConnectionIndex = 0;
else
m_nextConnectionIndex++;
}
else if (++m_nextConnectionIndex > maxIndex)
{
//went past end of vector, start back at 0
m_nextConnectionIndex = 0;
}
}while (con == NULL && m_nextConnectionIndex != startIndex);
return con;
}
//----------------------------------------
void GenericAPICore::countOpenConnections()
//----------------------------------------
{
m_currentConnections = 0;
m_maxConnections = m_serverConnections.size();
for (std::vector<GenericConnection *>::iterator conIter = m_serverConnections.begin(); conIter != m_serverConnections.end(); conIter++)
{
GenericConnection *con = *conIter;
if (con->isConnected())
++m_currentConnections;
}
}
//----------------------------------------
ServerTrackObject *GenericAPICore::findServer(unsigned server_track)
//----------------------------------------
{
std::map<unsigned, ServerTrackObject *>::iterator iter = m_serverTracks.find(server_track);
if (iter == m_serverTracks.end())
return NULL;
ServerTrackObject *stobj = (*iter).second;
m_serverTracks.erase(server_track);
return stobj;
}
#ifdef EXTERNAL_DISTRO
};
#endif
@@ -0,0 +1,121 @@
#if !defined (GENERICAPICORE_H_)
#define GENERICAPICORE_H_
//----------------------------------------
//
// WARNING: These files are NOT standard generic API files
// They have been modified for this project.
// Do NOT replace them with generic API files
//
//----------------------------------------
#pragma warning (disable: 4786)
#include <map>
#include <queue>
#include <time.h>
#include <Base/Archive.h>
#ifdef EXTERNAL_DISTRO
namespace NAMESPACE
{
#endif
class GenericRequest;
class GenericResponse;
class GenericConnection;
//----------------------------------------------
class ServerTrackObject
//----------------------------------------------
{
public:
ServerTrackObject(unsigned mapped_track, unsigned real_track, GenericConnection *con);
~ServerTrackObject() { }
inline GenericConnection *getConnection() { return m_connection; }
inline unsigned getRealServerTrack() { return m_realTrack; }
inline unsigned getMappedServerTrack() { return m_mappedTrack; }
private:
unsigned m_mappedTrack;
unsigned m_realTrack;
GenericConnection *m_connection;
};
//----------------------------------------------
class GenericAPICore
//----------------------------------------------
{
public:
friend class GenericConnection;
GenericAPICore(const char *host,
short port,
unsigned reqTimeout,
unsigned reconnectTimeout,
unsigned noDataTimeoutSecs = 5,
unsigned noAckTimeoutSecs = 5,
unsigned incomingBufSizeInKB = 32,
unsigned outgoingBufSizeInKB = 32,
unsigned keepAlive = 1,
unsigned maxRecvMessageSizeInKB = 0);
/**
* NOTE: arraySize must be actual size of host and port arrays.
* ALSO: cannot specify a 0 array size.
*/
GenericAPICore(const char *game, const char *hosts[],
const short port[],
unsigned arraySize,
unsigned reqTimeout,
unsigned reconnectTimeout,
unsigned noDataTimeoutSecs = 5,
unsigned noAckTimeoutSecs = 5,
unsigned incomingBufSizeInKB = 32,
unsigned outgoingBufSizeInKB = 32,
unsigned keepAlive = 1,
unsigned maxRecvMessageSizeInKB = 0);
virtual ~GenericAPICore();
void process();
virtual void responseCallback(short type, Base::ByteStream::ReadIterator &iter, GenericConnection *con) = 0;
virtual void responseCallback(GenericResponse *R) = 0;
virtual void OnDisconnect(GenericConnection *con) = 0;
virtual void OnConnect(GenericConnection *con) = 0;
void countOpenConnections();
ServerTrackObject *findServer(unsigned server_track);
void suspendProcessing() { m_suspended = true; }
void resumeProcessing() { m_suspended = false; }
unsigned submitRequest(GenericRequest *req, GenericResponse *res);
GenericConnection *getNextActiveConnection();
std::string &getGameCode() { return m_game; }
protected:
std::vector<GenericConnection *> m_serverConnections;
std::map<unsigned, GenericResponse *> m_pending;
std::queue<std::pair<GenericRequest *, GenericResponse *> > m_outboundQueue;
unsigned m_currTrack;
time_t m_reconnectTimeout;
unsigned m_outCount;
unsigned m_pendingCount;
unsigned m_requestTimeout;
unsigned m_currentConnections; // number currently connected
unsigned m_maxConnections; // number that should be connected
std::map<unsigned, ServerTrackObject *> m_serverTracks;
private:
bool m_suspended;
unsigned m_nextConnectionIndex;
std::string m_game;
};
#ifdef EXTERNAL_DISTRO
};
#endif
#endif
@@ -0,0 +1,209 @@
#include "GenericApiCore.h"
#include "GenericConnection.h"
#include "GenericMessage.h"
#include "CTCommon/CTEnum.h"
//----------------------------------------
//
// WARNING: These files are NOT standard generic API files
// They have been modified for this project.
// Do NOT replace them with generic API files
//
//----------------------------------------
#ifdef EXTERNAL_DISTRO
namespace NAMESPACE
{
#endif
using namespace std;
using namespace Base;
GenericConnection::GenericConnection(const char *host, short port, GenericAPICore *apiCore, unsigned reconnectTimeout, unsigned noDataTimeoutSecs, unsigned noAckTimeoutSecs, unsigned incomingBufSizeInKB, unsigned outgoingBufSizeInKB, unsigned keepAlive, unsigned maxRecvMessageSizeInKB)
: m_bConnected(CON_NONE),
m_apiCore(apiCore),
m_con(NULL),
m_host(host),
m_port(port),
m_lastTrack(123455), //random choice != 1
m_conState(CON_DISCONNECT),
m_reconnectTimeout(reconnectTimeout)
{
TcpManager::TcpParams params;
params.incomingBufferSize = incomingBufSizeInKB * 1024;
params.outgoingBufferSize = outgoingBufSizeInKB * 1024;
params.maxConnections = 1;
params.port = 0;
params.maxRecvMessageSize = maxRecvMessageSizeInKB*1024;
params.keepAliveDelay = keepAlive * 1000;
params.noDataTimeout = noDataTimeoutSecs * 1000;
//params.oldestUnacknowledgedTimeout = noAckTimeoutSecs * 1000;
m_manager = new TcpManager(params);
}
GenericConnection::~GenericConnection()
{
if(m_con)
{
m_con->SetHandler(NULL);
m_con->Disconnect();//don't worry about onterminated being called, we've set it's handler to null, so it wont
m_con->Release();
}
m_manager->Release();
}
void GenericConnection::disconnect()
{
if (m_con)
{
m_con->Disconnect();
//no need to release, since callback to onTerminated releases it, and callback is allways made m_con->Release();
m_con = NULL;
}
m_conState = CON_DISCONNECT;
m_bConnected = CON_NONE;
}
void GenericConnection::OnTerminated(TcpConnection *con)
{
// m_apiCore->OnDisconnect(m_host.c_str(), m_port);
m_apiCore->OnDisconnect(this);
if(m_con)
{
m_con->Release();
m_con = NULL;
}
m_conState = CON_DISCONNECT;
m_bConnected = CON_NONE;
}
void GenericConnection::OnRoutePacket(TcpConnection *con, const unsigned char *data, int dataLen)
{
short type;
unsigned track;
ByteStream msg(data, dataLen);
ByteStream::ReadIterator iter = msg.begin();
get(iter, type);
get(iter, track);
GenericResponse *res = NULL;
// the following if block is a temporary fix that prevents
// a crash with a game team in which they occasionally find
// themselves receiving a dupe track in consecutive calls to
// OnRoutePacket (which then leads to a callback being called
// twice and data being invalid on the second call -> crash!).
if (track != 0 &&
track == m_lastTrack)
{
printf("!!! ERROR !!! Got a duplicate track ID %u\n", track);
return;
}
m_lastTrack = track;
// end temporary fix.
if(track == 0) // notification message from the server, not as a response to a request from this API
{
if (type == CTService::CTGAME_REQUEST_CONNECT)
{ // this is a special case, for when we have identified our game code to server
m_bConnected = CON_IDENTIFIED;
m_apiCore->OnConnect(this);
}
else
{
m_apiCore->responseCallback(type, iter, this);
}
}
else
{
map<unsigned, GenericResponse *>::iterator mapIter = m_apiCore->m_pending.find(track);
if(mapIter != m_apiCore->m_pending.end())
{
res = (*mapIter).second;
iter = msg.begin();
res->unpack(iter);
m_apiCore->responseCallback(res);
m_apiCore->m_pendingCount--;
m_apiCore->m_pending.erase(mapIter);
delete res;
}
}
}
void GenericConnection::process()
{
switch(m_conState)
{
case CON_DISCONNECT:
// create connection object, attempting to connect and
// checking for connection in next state, CON_NEGOTIATE
m_con = m_manager->EstablishConnection(m_host.c_str(), m_port);
if(m_con)
{
m_con->SetHandler(this);
m_conState = CON_NEGOTIATE;
m_conTimeout = time(NULL) + m_reconnectTimeout;
}
break;
case CON_NEGOTIATE:
// check for connection
if(m_con->GetStatus() == TcpConnection::StatusConnected)
{
// we're connected
m_conState = CON_CONNECT;
m_bConnected = CON_CONNECTED;
// instead of calling OnConnect() right now, we are going to submit a connection packet
// identifying us
// m_apiCore->OnConnect(this);
Base::ByteStream msg;
put(msg, (short)CTService::CTGAME_REQUEST_CONNECT);
put(msg, (unsigned)0); // track
put(msg, (unsigned)API_VERSION_CODE);
put(msg, m_apiCore->getGameCode());
Send(msg);
}
else if(time(NULL) > m_conTimeout)
{
// we did not connect
m_con->Disconnect();
//no need to release, since callback to onTerminated releases it, and callback is allways made m_con->Release();
m_con = NULL;
m_conState = CON_DISCONNECT;
m_bConnected = CON_NONE;
}
break;
case CON_CONNECT:
// do nothing
break;
default:
// this should not occur, but we revert to CON_DISCONNECT if it does
m_conState = CON_DISCONNECT;
m_bConnected = CON_NONE;
if (m_con)
{
m_con->Disconnect();
//no need to release, since callback to onTerminated releases it, and callback is allways made m_con->Release();
m_con = NULL;
}
}
m_manager->GiveTime();
}
void GenericConnection::Send(Base::ByteStream &msg)
{
if(m_con && m_con->GetStatus() == TcpConnection::StatusConnected)
{
m_con->Send((const char *)msg.getBuffer(), msg.getSize());
}
}
#ifdef EXTERNAL_DISTRO
};
#endif
@@ -0,0 +1,81 @@
#if !defined (GENERICCONNECTION_H_)
#define GENERICCONNECTION_H_
//----------------------------------------
//
// WARNING: These files are NOT standard generic API files
// They have been modified for this project.
// Do NOT replace them with generic API files
//
//----------------------------------------
#include <Base/Archive.h>
#include <TcpLibrary/TcpManager.h>
#include <TcpLibrary/TcpConnection.h>
#include <TcpLibrary/TcpHandlers.h>
#ifdef EXTERNAL_DISTRO
namespace NAMESPACE
{
#endif
static const unsigned API_VERSION_CODE = 1;
enum eConState
{
CON_DISCONNECT,
CON_NEGOTIATE,
CON_CONNECT
};
enum eConnectStatus
{
CON_NONE,
CON_CONNECTED,
CON_IDENTIFIED
};
class GenericConnection : public TcpConnectionHandler
{
public:
GenericConnection(const char *host,
short port,
GenericAPICore *apiCore,
unsigned reconnectTimeout,
unsigned noDataTimeoutSecs = 5,
unsigned noAckTimeoutSecs = 5,
unsigned incomingBufSizeInKB = 32,
unsigned outgoingBufSizeInKB = 32,
unsigned keepAlive = 1,
unsigned maxRecvMessageSizeInKB = 0);
virtual ~GenericConnection();
virtual void OnRoutePacket(TcpConnection *con, const unsigned char *data, int dataLen);
virtual void OnTerminated(TcpConnection *con);
void Send(Base::ByteStream &msg);
inline const char *getHost() const { return m_host.c_str(); }
inline const short getPort() const { return m_port; }
inline eConnectStatus isConnected() { return m_bConnected; }
void disconnect();
void process();
private:
eConnectStatus m_bConnected;
GenericAPICore *m_apiCore;
TcpManager *m_manager;
TcpConnection *m_con;
std::string m_host;
short m_port;
unsigned m_lastTrack;
eConState m_conState;
time_t m_conTimeout;
unsigned m_reconnectTimeout;
};
#ifdef EXTERNAL_DISTRO
};
#endif
#endif
@@ -0,0 +1,44 @@
#include "GenericMessage.h"
//----------------------------------------
//
// WARNING: These files are NOT standard generic API files
// They have been modified for this project.
// Do NOT replace them with generic API files
//
//----------------------------------------
#ifdef EXTERNAL_DISTRO
namespace NAMESPACE
{
#endif
using namespace Base;
//-------------------------------------------
GenericRequest::GenericRequest(short type, unsigned server_track)
: m_type(type), m_server_track(server_track)
//-------------------------------------------
{
}
//-------------------------------------------
GenericResponse::GenericResponse(short type, unsigned result, void *user)
: m_type(type), m_result(result), m_user(user)
//-------------------------------------------
{
}
//-----------------------------------------
void GenericResponse::unpack(ByteStream::ReadIterator &iter)
//-----------------------------------------
{
get(iter, m_type);
get(iter, m_track);
get(iter, m_result);
}
#ifdef EXTERNAL_DISTRO
};
#endif
@@ -0,0 +1,75 @@
#if !defined (GENERICMESSAGE_H_)
#define GENERICMESSAGE_H_
//----------------------------------------
//
// WARNING: These files are NOT standard generic API files
// They have been modified for this project.
// Do NOT replace them with generic API files
//
//----------------------------------------
#include <time.h>
#include <Base/Archive.h>
#ifdef EXTERNAL_DISTRO
namespace NAMESPACE
{
#endif
//-------------------------------------------
class GenericRequest
//-------------------------------------------
{
public:
GenericRequest(short type, unsigned server_track = 0);
virtual ~GenericRequest() {};
virtual void pack(Base::ByteStream &msg) = 0;
short getType() const { return m_type; }
void setTimeout(time_t t) { m_timeout = t; }
time_t getTimeout() { return m_timeout; }
void setTrack(unsigned t) { m_track = t; }
unsigned getTrack() const { return m_track; }
inline const unsigned getMappedServerTrack() const { return m_server_track; }
inline void setServerTrack(unsigned track) { m_server_track = track; }
protected:
short m_type;
unsigned m_track;
time_t m_timeout;
unsigned m_server_track;
};
// Basic response message from server. In the case that this response to a request
// submitted from this API, the response would have been generated at request submission
// time, and the timeout value filled in appropriatly
//-------------------------------------------
class GenericResponse
//-------------------------------------------
{
public:
GenericResponse(short type, unsigned result, void *user);
virtual ~GenericResponse() {};
virtual void unpack(Base::ByteStream::ReadIterator &iter);
short getType() const { return m_type; }
void setTimeout(time_t t) { m_timeout = t; }
time_t getTimeout() { return m_timeout; }
void setTrack(unsigned t) { m_track = t; }
unsigned getTrack() const { return m_track; }
unsigned getResult() const { return m_result; }
void setResult(unsigned res) { m_result = res; }
void * getUser() const { return m_user; }
protected:
short m_type;
unsigned m_track;
unsigned m_result;
void *m_user;
time_t m_timeout;
};
#ifdef EXTERNAL_DISTRO
};
#endif
#endif