It was Simple afterall!
It needed an extra for(;;) loop inside, and a slight modification of the Logic!
the Client Socket produced by WSAAccept cannot be re-cycled, or re-generated! The User processing also needs three in stead of two Result States:-
enum{
CONTINUE_RUNNING=0,
END_CONVERSATION=1,
TERMINATE_SERVER=2,
};
The Dummy User Action is re_written as Follows:-
BOOL CSimpleSocketDlg::ProcessData(LPCSTR Input, CString& Result)
{
int RetVal=CONTINUE_RUNNING;
if(stricmp(Input,"<term>")==0){
Result="Terminating Server...";
RetVal= TERMINATE_SERVER;
}
if(stricmp(Input,"<end>")==0){
Result="Ending Conversation...";
RetVal= END_CONVERSATION;
}
else{
Result="<echo:... xmlns:echo="#unknown">";
Result+=Input;
}
return RetVal;
}
</echo:...></end></term>
The Main body ends up as follows:-
void CSimpleSocketDlg::Run()
{
WSADATA wsData;
sockaddr_in SA_IN;
DWORD u32_Error = WSAStartup(MAKEWORD(2,0), &wsData);
if (u32_Error)
return;
SOCKET hSock=socket(AF_INET, SOCK_STREAM,0);
SA_IN.sin_family=AF_INET;
SA_IN.sin_port = htons(2000);
SA_IN.sin_addr.s_addr =INADDR_ANY;
int err=bind(hSock,(struct sockaddr *) &SA_IN,sizeof(SA_IN));
if(err!=0)return;
for(;;){
listen(hSock,100);
struct sockaddr ClientIP;
SOCKET h_sockClient=WSAAccept ( hSock, &ClientIP,
NULL,AcceptCondition,(DWORD)this);
if(h_sockClient==INVALID_SOCKET){
err=WSAGetLastError();
return;
}
for(;;){
char Buf[4096]={0};
recv(h_sockClient,Buf,4096,0);
err=WSAGetLastError();
if(err==WSAECONNABORTED){
closesocket(h_sockClient); break;
}
CString Result;
int NextAction=ProcessData(Buf,Result);
if(send(h_sockClient,Result,Result.GetLength(),0)==SOCKET_ERROR ){
err=WSAGetLastError();
closesocket(h_sockClient);
break;
}
if(NextAction==CONTINUE_RUNNING)continue;
else if(NextAction==END_CONVERSATION){
closesocket(h_sockClient);
break;
}
else if(NextAction==TERMINATE_SERVER){
closesocket(h_sockClient);
return;
}
}
}
}
</term></end>
The above works extra fine in establishing connectivity and proving basic principles!
Notes.:
Single vs Multiple threads.
Any but the most basic Servers will need multiple threads. Otherwise, the server is blocked for the duration of a connection. However, for the purpose of debugging both Client and Server code, one would typically have One Client App, and One Server App,bouncing of eachother, on your own machine. Multiple threads have no advantage there, So I include a Single Threaded option, purely for debugging.
Thanks to all that took out the time to read my question, and to 'SA'who took the time to write a response.
:)