Main.cpp
#include <stdio.h>
#include "CServer.cpp"
class EventReceiver:
public CServer
{
void OnClientReceive(CServer* SVR)
{
char* Packet = SVR->GetReceivedBuffer();
int packetsize = SVR->GetReceivedSize();
PCLIENT_HANDLE clientthatsent = SVR->GetLatestReadClient();
printf("\n Packet Recieved - %s", Packet);
CLIENT_LIST_LOOP(SVR)
if(CUR_CLIENT_SOCKETID != clientthatsent->sSocketId)
{
SVR->SendPacketToClient(Packet,packetsize,CUR_CLIENT);
Sleep(250);
}
CLIENT_LIST_END_LOOP(SVR);
}
void OnClientConnection(CServer* SVR)
{
PCLIENT_HANDLE ConnectedClient = SVR->GetLatestConnectedClient();
printf("\n Client ( %s ) has connected!",ConnectedClient->szIpAddress);
}
};
int main()
{
CServer* Server = new CServer();
EventReceiver* MyEvents = new EventReceiver();
Server = MyEvents;
Server->SetPort(555);
Server->SetMaxClientAmmount(1000);
Server->StartServer();
while(1)
{
Sleep(1);
}
return 0;
}
CServer.cpp
#include "CServer.h"
CServer::CServer()
{
m_CurrentReceivingClient = 0x0;
m_CurrentAcceptingClient = 0x0;
m_ClientListHead = 0x0;
m_TotalClientCount = 0;
m_ClientCount = 0;
m_BufferSize = 0;
m_Port = 0;
m_MaxClient = 0;
m_ListeningSocket = 0;
m_isServerStarted = false;
m_BufferReceived = (char*)malloc(4096);
memset(m_BufferReceived,0,4096);
WSAStartup(MAKEWORD(2,2),&m_WSAData);
}
CServer::CServer(int nPort)
{
m_CurrentReceivingClient = 0x0;
m_CurrentAcceptingClient = 0x0;
m_ClientListHead = 0x0;
m_TotalClientCount = 0;
m_ClientCount = 0;
m_BufferSize = 0;
m_Port = nPort;
m_MaxClient = 0;
m_ListeningSocket = 0;
m_isServerStarted = false;
m_BufferReceived = (char*)malloc(4096);
memset(m_BufferReceived,0,4096);
WSAStartup(MAKEWORD(2,2),&m_WSAData);
}
CServer::~CServer()
{
m_isServerStarted = false;
free(m_BufferReceived);
WSACleanup();
}
void CServer::SetPort(int nPort)
{
m_Port = nPort;
}
bool CServer::StartServer()
{
m_ListeningSocket = socket(AF_INET,SOCK_STREAM,IPPROTO_TCP);
m_ServerAddress.sin_family = AF_INET;
m_ServerAddress.sin_addr.s_addr = INADDR_ANY;
m_ServerAddress.sin_port = htons(m_Port);
if(bind(m_ListeningSocket, (LPSOCKADDR)&m_ServerAddress, sizeof(struct sockaddr)) == SOCKET_ERROR)
{
return false;
}
m_isServerStarted = true;
CreateThread(NULL,0,(unsigned long (__stdcall *)(void *))StartAccepting,this,0,NULL);
CreateThread(NULL,0,(unsigned long (__stdcall *)(void *))StartReading,this,0,NULL);
return true;
}
void CServer::AddClient(SOCKET sSocketId,char* szIpAddress,PCLIENT_HANDLE pListHead)
{
if (!pListHead)
{
m_ClientListHead = (CLIENT_HANDLE*)malloc(sizeof(CLIENT_HANDLE));
memset(m_ClientListHead,0,sizeof(CLIENT_HANDLE));
pListHead = m_ClientListHead;
}
struct CLIENT_HANDLE* MyClients = pListHead;
while (MyClients->next != 0x0)
{
if(MyClients->sSocketId == sSocketId)
return;
MyClients = MyClients->next;
}
/* Set Up Client Information */
MyClients->sSocketId = sSocketId;
memset(MyClients->szIpAddress,0,32);
strcpy(MyClients->szIpAddress,szIpAddress);
MyClients->nClientNumber = m_TotalClientCount++;
m_CurrentAcceptingClient = MyClients;
/* End of Client Information Set Up */
MyClients->next = (CLIENT_HANDLE*)malloc(sizeof(CLIENT_HANDLE));
memset(MyClients->next,0x0,sizeof(CLIENT_HANDLE));
MyClients->next->previous = MyClients;
}
void CServer::RemoveClient(SOCKET sSocketId,PCLIENT_HANDLE pListHead)
{
struct CLIENT_HANDLE* MyClients = pListHead;
while (MyClients->next != 0x0)
{
if (MyClients->sSocketId == sSocketId)
{
if (MyClients->previous)
{
if (MyClients->next)
{
MyClients->previous->next = MyClients->next;
MyClients->next->previous = MyClients->previous;
}
else
MyClients->previous->next = 0x0;
free(MyClients);
}
else
{
if (MyClients->next)
{
m_ClientListHead = MyClients->next;
m_ClientListHead->previous = 0x0;
free(MyClients);
}
else
{
memset(MyClients,0x0,sizeof(CLIENT_HANDLE));
}
}
break;
}
else
{
MyClients = MyClients->next;
}
}
}
bool CServer::isServerStarted()
{
return m_isServerStarted;
}
DWORD CServer::StartAccepting(void* pParam)
{
((CServer*)pParam)->ClientAccepting();
return 0;
}
DWORD CServer::StartReading(void* pParam)
{
((CServer*)pParam)->ClientReading();
return 0;
}
int CServer::GetMaxClients()
{
return m_MaxClient;
}
int CServer::GetClientCount()
{
return m_ClientCount;
}
void CServer::ClientAccepting()
{
SOCKET sLatestClient = 0;
int length = sizeof(m_ServerAddress);
for(;;)
{
while ( listen( m_ListeningSocket, SOMAXCONN ) == SOCKET_ERROR );
if(GetMaxClients() == 0)
{
goto accept;
}
else
{
if(GetClientCount() < GetMaxClients())
{
goto accept;
}
else
{
goto end;
}
}
accept:
sLatestClient = accept(m_ListeningSocket,(LPSOCKADDR)&m_ServerAddress,&length);
if(sLatestClient != SOCKET_ERROR )
{
AddClient(sLatestClient,inet_ntoa(m_ServerAddress.sin_addr),m_ClientListHead);
m_ClientCount++;
if(m_CurrentAcceptingClient)
{
OnClientConnection(this);
}
m_CurrentAcceptingClient = 0x0;
}
end:
sLatestClient = 0;
}
}
void CServer::ClientReading()
{
int timer = 0;
static struct timeval timestruct;
timestruct.tv_sec = 0;
timestruct.tv_usec = 10;
int recvsize = 0;
while(1)
{
timer++;
if(timer > 50)
{
Sleep(1);
timer = 0;
}
PCLIENT_HANDLE MyClients = GetClientListHead();
if(MyClients)
{
while(MyClients->next)
{
timer++;
if(timer > 50)
{
Sleep(1);
timer = 0;
}
if(MyClients->sSocketId)
{
fd_set read;
FD_ZERO(&read);
FD_SET(MyClients->sSocketId,&read);
select(MyClients->sSocketId+1,&read,0x0,0x0,×truct);
if(FD_ISSET(MyClients->sSocketId,&read))
{
memset(m_BufferReceived,0,4096);
recvsize = recv(MyClients->sSocketId,m_BufferReceived,4096,0);
if(recvsize > 0)
{
m_CurrentReceivingClient = MyClients;
m_BufferSize = recvsize;
OnClientReceive(this);
}
else
{
Sleep(1);
closesocket(MyClients->sSocketId);
RemoveClient(MyClients->sSocketId,m_ClientListHead);
MyClients = m_ClientListHead;
m_ClientCount--;
}
}
FD_ZERO(&read);
}
if(MyClients)
{
if(MyClients->next)
MyClients = MyClients->next;
}
else
break;
}
}
}
}
PCLIENT_HANDLE CServer::GetLatestReadClient()
{
return m_CurrentReceivingClient;
}
PCLIENT_HANDLE CServer::GetLatestConnectedClient()
{
return m_CurrentAcceptingClient;
}
PCLIENT_HANDLE CServer::GetClientListHead()
{
return m_ClientListHead;
}
char* CServer::GetReceivedBuffer()
{
return m_BufferReceived;
}
int CServer::GetReceivedSize()
{
return m_BufferSize;
}
int CServer::SetMaxClientAmmount(int nAmmount)
{
m_MaxClient = nAmmount;
return m_MaxClient;
}
int CServer::SendPacketToClient(char* pPacket, int nSize,PCLIENT_HANDLE pClientHandle)
{
return send(pClientHandle->sSocketId,pPacket,nSize,0);
}
int CServer::SendPacketToAllClients(char *pPacket, int nSize)
{
PCLIENT_HANDLE MyClients = GetClientListHead();
while(MyClients->next)
{
if(MyClients->sSocketId)
{
send(MyClients->sSocketId,pPacket,nSize,0);
}
MyClients = MyClients->next;
}
return 1;
}
CServer.h
#ifdef WIN32
#include <windows.h>
#endif
#ifdef WIN32_LEAN_AND_MEAN
#include <winsock2.h>
#endif
#pragma comment(lib,"ws2_32.lib")
typedef struct CLIENT_HANDLE
{
CLIENT_HANDLE* previous;
SOCKET sSocketId;
int nClientNumber;
char szIpAddress[32];
CLIENT_HANDLE* next;
}CLIENT_HANDLE,*PCLIENT_HANDLE;
PCLIENT_HANDLE MyClients;
#define CLIENT_LIST_LOOP(a) MyClients = a->GetClientListHead(); \
while(MyClients->next) {
#define CLIENT_LIST_END_LOOP(a) MyClients = MyClients->next; }
#define CUR_CLIENT MyClients
#define CUR_CLIENT_IP MyClients->szIpAddress
#define CUR_CLIENT_SOCKETID MyClients->sSocketId
#define CUR_CLIENT_ID MyClients->nClientNumber
class CServer
{
// ---------------------
// Private delcaration
private:
PCLIENT_HANDLE m_ClientListHead;
PCLIENT_HANDLE m_CurrentAcceptingClient;
PCLIENT_HANDLE m_CurrentReceivingClient;
int m_TotalClientCount;
int m_MaxClient;
int m_ClientCount;
int m_BufferSize;
char* m_BufferReceived;
bool m_isServerStarted;
void AddClient(SOCKET sSocketId,char* szIpAddress,PCLIENT_HANDLE pListHead);
void RemoveClient(SOCKET sSocketId,PCLIENT_HANDLE pListHead);
void ClientAccepting();
static DWORD StartAccepting(void* pParam);
void ClientReading();
static DWORD StartReading(void* pParam);
// ---------------------
// Protected declaration
protected:
SOCKADDR_IN m_ServerAddress;
SOCKET m_ListeningSocket;
WSADATA m_WSAData;
int m_Port;
// ---------------------
// Public delcaration
public:
CServer();
CServer(int nPort);
~CServer();
void SetPort(int nPort);
virtual void OnClientReceive(CServer*){};
virtual void OnClientConnection(CServer*){};
PCLIENT_HANDLE GetLatestReadClient();
PCLIENT_HANDLE GetLatestConnectedClient();
PCLIENT_HANDLE GetClientListHead();
int SendPacketToClient(char* pPacket,int nSize,PCLIENT_HANDLE pClientHandle);
int SendPacketToAllClients(char* pPacket,int nSize);
bool StartServer();
bool isServerStarted();
char* GetReceivedBuffer();
int GetReceivedSize();
int SetMaxClientAmmount(int nAmmount);
int GetClientCount();
int GetPort();
int GetMaxClients();
};
ERRORS:
--------------------Configuration: Chat Server - Win32 Release--------------------
Compiling...
CServer.cpp
Main.cpp
Generating Code...
Linking...
Main.obj : error LNK2005: "public: __thiscall CServer::CServer(void)" (??0CServer@@QAE@XZ) already defined in CServer.obj
Main.obj : error LNK2005: "public: __thiscall CServer::CServer(int)" (??0CServer@@QAE@H@Z) already defined in CServer.obj
Main.obj : error LNK2005: "public: __thiscall CServer::~CServer(void)" (??1CServer@@QAE@XZ) already defined in CServer.obj
Main.obj : error LNK2005: "public: void __thiscall CServer::SetPortA(int)" (?SetPortA@CServer@@QAEXH@Z) already defined in CServer.obj
Main.obj : error LNK2005: "public: bool __thiscall CServer::StartServer(void)" (?StartServer@CServer@@QAE_NXZ) already defined in CServer.obj
Main.obj : error LNK2005: "private: void __thiscall CServer::AddClient(unsigned int,char *,struct CLIENT_HANDLE *)" (?AddClient@CServer@@AAEXIPADPAUCLIENT_HANDLE@@@Z) already defined in CServer.obj
Main.obj : error LNK2005: "private: void __thiscall CServer::RemoveClient(unsigned int,struct CLIENT_HANDLE *)" (?RemoveClient@CServer@@AAEXIPAUCLIENT_HANDLE@@@Z) already defined in CServer.obj
Main.obj : error LNK2005: "public: bool __thiscall CServer::isServerStarted(void)" (?isServerStarted@CServer@@QAE_NXZ) already defined in CServer.obj
Main.obj : error LNK2005: "private: static unsigned long __cdecl CServer::StartAccepting(void *)" (?StartAccepting@CServer@@CAKPAX@Z) already defined in CServer.obj
Main.obj : error LNK2005: "private: static unsigned long __cdecl CServer::StartReading(void *)" (?StartReading@CServer@@CAKPAX@Z) already defined in CServer.obj
Main.obj : error LNK2005: "public: int __thiscall CServer::GetMaxClients(void)" (?GetMaxClients@CServer@@QAEHXZ) already defined in CServer.obj
Main.obj : error LNK2005: "public: int __thiscall CServer::GetClientCount(void)" (?GetClientCount@CServer@@QAEHXZ) already defined in CServer.obj
Main.obj : error LNK2005: "private: void __thiscall CServer::ClientAccepting(void)" (?ClientAccepting@CServer@@AAEXXZ) already defined in CServer.obj
Main.obj : error LNK2005: "private: void __thiscall CServer::ClientReading(void)" (?ClientReading@CServer@@AAEXXZ) already defined in CServer.obj
Main.obj : error LNK2005: "public: struct CLIENT_HANDLE * __thiscall CServer::GetLatestReadClient(void)" (?GetLatestReadClient@CServer@@QAEPAUCLIENT_HANDLE@@XZ) already defined in CServer.obj
Main.obj : error LNK2005: "public: struct CLIENT_HANDLE * __thiscall CServer::GetLatestConnectedClient(void)" (?GetLatestConnectedClient@CServer@@QAEPAUCLIENT_HANDLE@@XZ) already defined in CServer.obj
Main.obj : error LNK2005: "public: struct CLIENT_HANDLE * __thiscall CServer::GetClientListHead(void)" (?GetClientListHead@CServer@@QAEPAUCLIENT_HANDLE@@XZ) already defined in CServer.obj
Main.obj : error LNK2005: "public: char * __thiscall CServer::GetReceivedBuffer(void)" (?GetReceivedBuffer@CServer@@QAEPADXZ) already defined in CServer.obj
Main.obj : error LNK2005: "public: int __thiscall CServer::GetReceivedSize(void)" (?GetReceivedSize@CServer@@QAEHXZ) already defined in CServer.obj
Main.obj : error LNK2005: "public: int __thiscall CServer::SetMaxClientAmmount(int)" (?SetMaxClientAmmount@CServer@@QAEHH@Z) already defined in CServer.obj
Main.obj : error LNK2005: "public: int __thiscall CServer::SendPacketToClient(char *,int,struct CLIENT_HANDLE *)" (?SendPacketToClient@CServer@@QAEHPADHPAUCLIENT_HANDLE@@@Z) already defined in CServer.obj
Main.obj : error LNK2005: "public: int __thiscall CServer::SendPacketToAllClients(char *,int)" (?SendPacketToAllClients@CServer@@QAEHPADH@Z) already defined in CServer.obj
Main.obj : error LNK2005: "struct CLIENT_HANDLE * MyClients" (?MyClients@@3PAUCLIENT_HANDLE@@A) already defined in CServer.obj
Release/Chat Server.exe : fatal error LNK1169: one or more multiply defined symbols found
Error executing link.exe.
Chat Server.exe - 24 error(s), 0 warning(s)