Winsock Tutorial 2

Blocking Sockets in TCP/IP (The Server)

This tutorial is designed to be a companion to our previous client tutorial. By the end of this tutorial we will be able to run our client and server together for some basic networking.

Prerequisties

Project type: Console
Include files: winsock2.h, iostream.h
Library files: ws2_32.lib



The Server

Setting up a server is relatively simple once you know how. As you will soon see, most of the code is the same as the client, with a few alterations.

As before we first need to initialise Winsock.

WSADATA WsaDat;
WSAStartup(MAKEWORD(2,2),&WsaDat);


And then setup our socket.

SOCKET Socket=socket(AF_INET,SOCK_STREAM,IPPROTO_TCP);

So far our code is identical. We can now skip the gethostbyname() function as the server does not need to connect to the client, it will wait for clients to connect to it.

Next we fill out our SOCKADDR_IN struct as we did before, but in this case we are setting up what we want our server to listen for. In our case we want the server to listen to any available adapter (INADDR_ANY). You could specify to listen from a particular IP address if you wanted to. But, generally we are happy to listen from any available address. And once again we are going to use port 8888 as we did with the client, so they can be used to communicate with each other.

SOCKADDR_IN serverInf;
serverInf.sin_family=AF_INET;
serverInf.sin_addr.s_addr=INADDR_ANY;
serverInf.sin_port=htons(8888);

From here we can then 'bind' our serverInf to our socket we created earlier.

bind(Socket,(SOCKADDR*)(&serverInf),sizeof(serverInf);
And then we can 'listen' on our socket for incoming connections.

listen(Socket,1);
Once our client connects to our server we can accept the connection and send and recieve data as we please.

accept(Socket,NULL,NULL);
As with our client. When we are finished, we need shutdown our socket, close it, and then clean up Winsock.

shutdown(Socket,SD_SEND);
closesocket(Socket);
WSACleanup();

The Full Code

#include <iostream>
#include <winsock2.h>
#pragma comment(lib,"ws2_32.lib")

int main()
{
	WSADATA WsaDat;
	if(WSAStartup(MAKEWORD(2,2),&WsaDat)!=0)
	{
		std::cout<<"WSA Initialization failed!\r\n";
		WSACleanup();
		system("PAUSE");
		return 0;
	}
	
	SOCKET Socket=socket(AF_INET,SOCK_STREAM,IPPROTO_TCP);
	if(Socket==INVALID_SOCKET)
	{
		std::cout<<"Socket creation failed.\r\n";
		WSACleanup();
		system("PAUSE");
		return 0;
	}
	
	SOCKADDR_IN serverInf;
	serverInf.sin_family=AF_INET;
	serverInf.sin_addr.s_addr=INADDR_ANY;
	serverInf.sin_port=htons(8888);

	if(bind(Socket,(SOCKADDR*)(&serverInf),sizeof(serverInf))==SOCKET_ERROR)
	{
		std::cout<<"Unable to bind socket!\r\n";
		WSACleanup();
		system("PAUSE");
		return 0;
	}

	listen(Socket,1);

	SOCKET TempSock=SOCKET_ERROR;
	while(TempSock==SOCKET_ERROR)
	{
		std::cout<<"Waiting for incoming connections...\r\n";
		TempSock=accept(Socket,NULL,NULL);
	}
	Socket=TempSock;
std::cout<<"Client connected!\r\n\r\n"; char *szMessage="Welcome to the server!\r\n"; send(Socket,szMessage,strlen(szMessage),0); // Shutdown our socket shutdown(Socket,SD_SEND); // Close our socket entirely closesocket(Socket); // Cleanup Winsock WSACleanup(); system("PAUSE"); return 0; }


Things to try

Try sending and recieving data to and from your server using the send() and recv() functions.

Additional informaton

For additional information we have provided the following link.

Microsoft (MSDN) - Getting started with Winsock


Next tutorial

Tutorial 3 - Non-Blocking Sockets in TCP/IP (The Client)