Page 297 - DCAP403_Operating System
P. 297
Operating System
Notes Listening on an INET BSD Socket
Once a socket has had an address bound to it, it may listen for incoming connection requests
specifying the bound addresses. A network application can listen on a socket without fi rst binding
an address to it; in this case the INET socket layer finds an unused port number (for this protocol)
and automatically binds it to the socket. The listen socket function moves the socket into state
TCP_LISTEN and does any network specific work needed to allow incoming connections.
For UDP sockets, changing the socket’s state is enough but TCP now adds the socket’s sock data
structure into two hash tables as it is now active. These are the tcp_bound_hash table and the
tcp_listening_hash. Both are indexed via a hash function based on the IP port number.
Whenever an incoming TCP connection request is received for an active listening socket, TCP
builds a new sock data structure to represent it. This sock data structure will become the bottom
half of the TCP connection when it is eventually accepted. It also clones the incoming sk_buff
containing the connection request and queues it onto the receive_queue for the listening sock
data structure. The clone sk_buff contains a pointer to the newly created sock data structure.
Accepting Connection Requests
UDP does not support the concept of connections, accepting INET socket connection requests
only applies to the TCP protocol as an accept operation on a listening socket causes a new socket
data structure to be cloned from the original listening socket. The accept operation is then passed
to the supporting protocol layer, in this case INET to accept any incoming connection requests.
The INET protocol layer will fail the accept operation if the underlying protocol, say UDP, does
not support connections. Otherwise the accept operation is passed through to the real protocol,
in this case TCP. The accept operation can be either blocking or non-blocking. In the non-blocking
case if there are no incoming connections to accept, the accept operation will fail and the newly
created socket data structure will be thrown away. In the blocking case the network application
performing the accept operation will be added to a wait queue and then suspended until a
TCP connection request is received. Once a connection request has been received the sk_buff
containing the request is discarded and the sock data structure is returned to the INET socket
layer where it is linked to the new socket data structure created earlier. The file descriptor (fd)
number of the new socket is returned to the network application, and the application can then
use that file descriptor in socket operations on the newly created INET BSD socket.
13.9.5 The IP Layer
Socket Buffers
One of the problems of having many layers of network protocols, each one using the services of
another, is that each protocol needs to add protocol headers and tails to data as it is transmitted
and to remove them as it processes received data. This make passing data buffers between the
protocols difficult as each layer needs to find where its particular protocol headers and tails
are. One solution is to copy buffers at each layer but that would be inefficient. Instead, Linux
uses socket buffers or sk_buffs to pass data between the protocol layers and the network device
drivers. sk_buffs contain pointer and length fields that allow each protocol layer to manipulate
the application data via standard functions or ``methods’’.
Figure 13.15 shows the sk_buff data structure; each sk_buff has a block of data associated with it.
The sk_buff has four data pointers, which are used to manipulate and manage the socket buffer’s
data:
Head: Points to the start of the data area in memory. This is fixed when the sk_buff and its
associated data block is allocated.
290 LOVELY PROFESSIONAL UNIVERSITY