Programming with sockets

Connection establishment

Connection establishment is usually asymmetric, with one process a client and the other a server. The server, when willing to offer its advertised services, binds a socket to a well-known address associated with the service and then passively listens on its socket. It is then possible for an unrelated process to rendezvous with the server. The client requests services from the server by initiating a connection to the server's socket. On the client side the connect call is used to initiate a connection. In the UNIX domain, this might appear as:

   struct sockaddr_un server;
   connect(s, (struct sockaddr *)&server,
   	strlen(server.sun_path) + offsetof(struct sockaddr_un, sun_path));
while in the Internet domain, it might be:
   struct sockaddr_in server;
   connect(s, (struct sockaddr *)&server, sizeof(server));
server would contain either the UNIX pathname, or the Internet address and port number of the server to which the client process wishes to speak. If the client process's socket is unbound at the time of the connect call, the system will automatically select and bind a name to the socket if necessary. See ``Signals and process groups'' below. This is the usual way that local addresses are bound to a socket.

An error is returned if the connection was unsuccessful (however, any name automatically bound by the system remains). Otherwise, the socket is associated with the server and data transfer may begin. Some of the more common errors returned when a connection attempt fails are:

After failing to establish a connection over a period of time, the system stopped attempting the connection. This may occur when the destination host is down or when problems in the network result in lost transmissions.

The host refused service. This usually occurs when a server process is not present at the requested name.

These operational errors are returned based on status information delivered to the client host by the underlying communication services.

These operational errors can occur either because the network or host is unknown (no route to the network or host is present), or because of status information returned by intermediate gateways or switching nodes. The status returned is not always sufficient to distinguish between a network that is down and a host that is down.
For a server to receive a client's connection it must perform two steps after binding its socket. The first is to listen for incoming connection requests. With a socket marked as listening, the second step is to accept a connection:
   struct sockaddr_in from;
   listen(s, 5);
   fromlen = sizeof(from);
   newsock = accept(s, (struct sockaddr *)&from, &fromlen);
The first parameter to the listen call is the socket on which the connection is to be established. The second parameter to the listen call specifies the maximum number of outstanding connections that may be queued awaiting acceptance by the server process. (For the UNIX domain, from would be declared as a
   struct sockaddr_un
but nothing different would need to be done as far as fromlen is concerned. In the examples that follow, only Internet routines will be discussed.) A new descriptor is returned on receipt of a connection (along with a new socket). If the server wishes to find out who its client is, it may supply a buffer for the client socket's name. The value-result parameter fromlen is initialized by the server to show how much space is associated with from. It is then modified on return to reflect the true size of the name. If the client's name is not of interest, the second parameter may be a null pointer.

accept normally blocks. That is, accept will not return until a connection is available or the system call is interrupted by a signal to the process. Further, there is no way for a process to show that it will accept connections only from a specific individual or individuals. It is up to the user process to consider who the connection is from and close down the connection if it does not want to speak to the process. If the server process wants to accept connections on more than one socket, or wants to avoid blocking on the accept call, there are alternatives; they will be considered in ``Advanced topics''.

© 2005 The SCO Group, Inc. All rights reserved.
SCO OpenServer Release 6.0.0 -- 02 June 2005