I have built a simple c TCP server and client using winsock. The code all compiles without error however either the server is refusing connections or my client is failing to connect properly.
The code is alot to put onto stackoverflow so here is a pastebin for the server and Client.
https://pastebin.com/ZQavPxsR - Server Code
https://pastebin.com/cLFVp2B1 - Client Code
sockaddr_in clientService;
clientService.sin_family = AF_INET;
InetPton(AF_INET, _T("127.0.0.1"), &clientService.sin_addr.s_addr);
clientService.sin_port = htons(port);
if (connect(clientSocket, (SOCKADDR*)&clientService, sizeof(clientService)) == SOCKET_ERROR)
{
std::cout << "Client: connect() = Failed to connect." << std::endl;
WSACleanup();
system("pause");
return 0;
}
else
{
std::cout << "Client: connect() is OK." << std::endl;
std::cout << "Client: Can start sending and reciving data... " << std::endl;
}
Above is a snippet of the code that is from the client and is responsible for making the connection with the server.
acceptSocket = accept(serverSocket, NULL, NULL);
if (acceptSocket == INVALID_SOCKET)
{
std::cout << "Accept Failed: " << WSAGetLastError() << std::endl;
WSACleanup();
return -1;
}
else
{
std::cout << "Accepted connection " << std::endl;
system("pause");
WSACleanup();
}
Above is a snippet of the code that is from the server and is responsible for accepting the connection with the client.
CodePudding user response:
Your server is not initializing the service.sin_port field before calling bind(), so the code exhibits undefined behavior. Your listening socket will end up trying to bind to whatever random port value was already present in the memory that the sin_port field occupies. And if that value happens to be 0, then bind() will choose a random port from Windows' available ephemeral ports. In any case, it is very unlikely that your server is ever going to be listening on port 4679, which is the port the client is trying to connect to.
On a side note, there are some other problems with your code:
In both client and server, your calls to
InetPton()should be passing in a pointer to thesockaddr_in::sin_addrfield, not thesockaddr_in::sin_addr.s_addrfield. It "works" only becauses_addris the sole data member ofsin_addrand thus they have the same memory address. But technically, this is undefined behavior sinceInetPton()wants anIN_ADDR*not aULONG*.Your server is not exiting if
listen()fails, is leakingserverSocketwhetheraccept()succeeds or fails, and is leakingacceptSocketifaccept()succeeds.Your client is leaking
clientSocketwhetherconnect()succeeds or fails.
