After a couple hours of programming I finaly manage to do this:
Code:
#include <iostream>
#include <winsock2.h>
#include <windows.h>
using namespace std;
#define version 0x002
#define PORT 5193
#define MAX_CON 5
#define BUFFER_SIZE 1024
DWORD Server();
DWORD Session(void*,int);
HANDLE hSemaphore; /* counter of simultaneuos connections */
HANDLE hSessionStarted; /* event that session is started */
SOCKET serverSocket;
int main()
{
WSADATA wsaData;
DWORD ThreadID;
HANDLE Thread;
WSAStartup(version,&wsaData);
Thread=CreateThread(0,0,(LPTHREAD_START_ROUTINE)Server,0,0,&ThreadID);
hSemaphore=CreateSemaphore(NULL,MAX_CON, MAX_CON,NULL);
hSessionStarted = CreateEvent(NULL,FALSE,FALSE,NULL);
WaitForSingleObject(Thread,INFINITE);
WSACleanup();
}
int ID=0;//ID number for connections
DWORD Server()
{
SOCKET serverSocket,clientSocket;
sockaddr_in serverSockAddr,clientSockAddr;
protoent *pProto;
DWORD ThID;
ZeroMemory(&serverSockAddr,sizeof(serverSockAddr));
ZeroMemory(&clientSockAddr,sizeof(clientSockAddr));
serverSockAddr.sin_family=AF_INET;
serverSockAddr.sin_port=htons(PORT);
serverSockAddr.sin_addr.S_un.S_addr=htonl(INADDR_ANY);
pProto=getprotobyname("tcp");
serverSocket=socket(AF_INET,SOCK_STREAM,pProto->p_proto);
if(serverSocket==INVALID_SOCKET)
{
cout<<"Error! Cannot create socket!"<<endl;
ExitThread(0);
return 0;
}
if(bind(serverSocket,(const sockaddr*)&serverSockAddr,sizeof(serverSockAddr))==SOCKET_ERROR)
{
cout<<"Error! Cannot bind socket!"<<endl;
ExitThread(0);
return 0;
}
if(listen(serverSocket,MAX_CON)==SOCKET_ERROR)
{
cout<<"Error! Cannot listen socket!"<<endl;
ExitThread(0);
return 0;
}
cout<<"Listening for incomming connections!"<<endl;
int aLen=sizeof(clientSockAddr);
while(true)
{
clientSocket=accept(serverSocket,(sockaddr*)&clientSockAddr,&aLen);
if(clientSocket == SOCKET_ERROR)
{
cout<<"Error! Cannot accept connection!"<<endl;
break;
}
ID++;
if(WaitForSingleObject(hSemaphore,0) == WAIT_OBJECT_0)
{
CreateThread(NULL, 0, (LPTHREAD_START_ROUTINE)Session, (void*)&clientSocket, 0, &ThID);
switch (WaitForSingleObject(hSessionStarted, 5000L))
{
case WAIT_OBJECT_0:
break;
case WAIT_TIMEOUT:
/* stop service */
cout<<"Error"<<endl;
ExitThread(0);
return 0;
}
}
else
{
closesocket(clientSocket);
}
}
ExitThread(0);
return 0;
}
DWORD Session(void* client, int ID)
{
SOCKET clientSocket=*(SOCKET *)client;
int get;
char msg[BUFFER_SIZE];
PulseEvent(hSessionStarted);
while(true)
{
get=recv(clientSocket,msg,BUFFER_SIZE,0);
if(get==SOCKET_ERROR)
{
std::cout<<"Receiving error!"<<std::endl;
ExitThread(0);
return 0;
}
if(get==0)
{
cout<<"Transmission number: "<<ID<<" ended"<<endl;
ID--;
break;
}
else
{
std::cout<<msg<<std::endl;
}
}
ReleaseSemaphore(hSemaphore, 1, NULL);
ExitThread(0);
return 0;
}
I don't know if you meant this when you suggested me a multithreading solution. I think this is good, but there are some things that I'm not sure about, especially with position of ReleaseSemaphore.
If you can take and examine this code just to make sure everything is ok. I out global variable ID to distinguish connections and it seems that this solution doesn't work, because my ID variable don't increment. I don't know why.