100% found this document useful (1 vote)
102 views

Advanced IO Finctions

The document discusses advanced I/O functions in Linux including: 1. Socket timeouts that allow placing timeouts on socket I/O operations using select, alarm, or SO_RCVTIMEO/SO_SNDTIMEO options. 2. Functions like recv, send, readv, writev, recvmsg and sendmsg that allow reading from and writing to sockets. 3. recvmsg and sendmsg are the most general functions and can replace calls to read, readv, recv, and recvfrom for receiving as well as the various output functions for sending. They support scatter-gather I/O, protocol addresses, and ancillary data.

Uploaded by

sukumargac
Copyright
© Attribution Non-Commercial (BY-NC)
Available Formats
Download as PPT, PDF, TXT or read online on Scribd
100% found this document useful (1 vote)
102 views

Advanced IO Finctions

The document discusses advanced I/O functions in Linux including: 1. Socket timeouts that allow placing timeouts on socket I/O operations using select, alarm, or SO_RCVTIMEO/SO_SNDTIMEO options. 2. Functions like recv, send, readv, writev, recvmsg and sendmsg that allow reading from and writing to sockets. 3. recvmsg and sendmsg are the most general functions and can replace calls to read, readv, recv, and recvfrom for receiving as well as the various output functions for sending. They support scatter-gather I/O, protocol addresses, and ancillary data.

Uploaded by

sukumargac
Copyright
© Attribution Non-Commercial (BY-NC)
Available Formats
Download as PPT, PDF, TXT or read online on Scribd
You are on page 1/ 14

Advanced I/O Functions

• Socket timeouts
• recv and send functions
• readv and writev functions
• recvmsg and sendmsg functions
• Ancillary data
• T/TCP: TCP for transactions

1
Socket Timeouts
• There are three ways to place a timeout on an I/O operation involving a
socket:
1. Call alarm which generates SIGALRM before calling socket functions.
2. Block waiting for I/O in select which has a time limit built in, instead of blocking
in a call to read or write.
3. Set SO_RCVTIMEO and SO_SNDTIMEO socket options by setsockopt. The
problem with this approach is that not all implementations support these two
socket options.
• All three techniques work with input and output operations, could also use
with connect. Since a TCP connect can take a long time to time out (typically
75 seconds). select can be used to place a timeout on connect only when the
socket is in a nonblocking mode.
• Also note that the first two techniques work with any descriptor, while the
third technique works only with socket descriptors.

2
connect with a timeout
static void connect_alarm(int);
int connect_timeo(int sockfd, const SA *saptr, socklen_t salen, int nsec)
{ Sigfunc *sigfunc;
int n;
sigfunc = Signal(SIGALRM, connect_alarm);
if (alarm(nsec) != 0)
err_msg("connect_timeo: alarm was already set");
if ( (n = connect(sockfd, saptr, salen)) < 0) {
close(sockfd);
if(errno == EINTR)
errno = ETIMEDOUT;
}
alarm(0); /* turn off the alarm */
Signal(SIGALRM, sigfunc); /* restore previous signal handler */
return (n);
}
static void connect_alarm(int signo) {
return; /* just interrupt the connect() */
}

3
dg_cli function with alarm to timeout recvfrom
• static void sig_alrm(int);
void dg_cli(FILE *fp, int sockfd, const SA *pservaddr, socklen_t servlen) {
int n;
char sendline[MAXLINE], recvline[MAXLINE + 1];
Signal(SIGALRM, sig_alrm);
while (Fgets(sendline, MAXLINE, fp) != NULL) {
Sendto(sockfd, sendline, strlen(sendline), 0, pservaddr, servlen);
alarm(5);
if ( (n = recvfrom(sockfd, recvline, MAXLINE, 0, NULL, NULL)) < 0){
if (errno == EINTR)
fprintf(stderr, "socket timeout\n");
else
err_sys("recvfrom error");
}
else { alarm(0);
recvline[n] = 0; /* null terminate */
Fputs(recvline, stdout);
}
}
}
static void sig_alrm(int signo) {
return; /* just interrupt the recvfrom() */
}
4
waits for a descriptor to become readable
• int readable_timeo(int fd, int sec)
{
fd_set rset;
struct timeval tv;
FD_ZERO(&rset);
FD_SET(fd, &rset);
tv.tv_sec = sec;
tv.tv_usec = 0;
return (select(fd + 1, &rset, NULL, NULL, &tv));
/* > 0 if descriptor is readable */
}

5
SO_RCVTIMEO socket option to set a timeout
• void dg_cli(FILE *fp, int sockfd, const SA *pservaddr, socklen_t servlen)
{
int n;
char sendline[MAXLINE], recvline[MAXLINE + 1];
struct timeval tv;
tv.tv_sec = 5;
tv.tv_usec = 0;
Setsockopt(sockfd, SOL_SOCKET, SO_RCVTIMEO, &tv, sizeof(tv));
while (Fgets(sendline, MAXLINE, fp) != NULL) {
Sendto(sockfd, sendline, strlen(sendline), 0, pservaddr, servlen);
n = recvfrom(sockfd, recvline, MAXLINE, 0, NULL, NULL);
if (n < 0) {
if (errno == EWOULDBLOCK) {
fprintf(stderr, "socket timeout\n");
continue;
} else
err_sys("recvfrom error");

recvline[n] = 0; /* null terminate */
Fputs(recvline, stdout);
}
} 6
recv and send Functions
• #include <sys/socket.h>
ssize_t recv(int sockfd, void *buff, size_t nbytes, int flags);
ssize_t send(int sockfd, const void *buff, size_t nbytes, int flags);
Both return: number of bytes read or written if OK, –1 on error
• The first three arguments to recv and send are the same as the first three arguments to
read and write.
• The flags argument is either 0 or is formed by logically OR'ing one or more of the
constants shown in Figure .

flags Description recv send


MSG_DONTROUTE bypass routing table lookup X
MSG_DONTWAIT only this operation is nonblocking X X
MSG_OOB send or receive out-of-band data X X
MSG_PEEK peek at incoming message X
MSG_WAITALL wait for all the data X

7
readv and writev Functions
• readv and writev let us read into or write from one or more buffers with a single
function call.
• These operations are called scatter read (since the input data is scattered into
multiple application buffers) and gather write (since multiple buffers are
gathered for a single output operation).
• #include <sys/uio.h>
ssize_t readv(int filedes, const struct iovec *iov, int iovcnt);
ssize_t writev(int filedes, const struct iovec *iov, int iovcnt);
Both return: number of bytes read or written, –1 on error
struct iovec {
void *iov_base; /* starting address of buffer */
size_t iov_len; /* size of buffer */
};
• The second argument to both functions is a pointer to an array of iovec
structures, which is defined by including the <sys/uio.h> header.
• The readv and writev functions can be used with any descriptor, not just
sockets. Also, writev is an atomic operation.
8
recvmsg and sendmsg Functions
• These two functions are the most general of all the I/O functions. W
• We could replace all calls to read, readv, recv, and recvfrom with calls to recvmsg. All
calls to the various output functions could be replaced with calls to sendmsg.
• #include <sys/socket.h>
ssize_t recvmsg(int sockfd, struct msghdr *msg, int flags);
ssize_t sendmsg(int sockfd, struct msghdr *msg, int flags);
Both return: number of bytes read or written if OK, –1 on error
• struct msghdr {
void *msg_name; /* protocol address */
socklen_t msg_namelen; /* size of protocol address */
struct iovec *msg_iov; /* scatter/gather array */
int msg_iovlen; /* # elements in msg_iov */
void *msg_control; /* ancillary data (cmsghdr struct) */
socklen_t msg_controllen; /* length of ancillary data */
int msg_flags; /* flags returned by recvmsg() */
};

9
recvmsg and sendmsg Functions
• The msg_name and msg_namelen members are used when the socket is not connected
(e.g., an unconnected UDP socket). They are similar to the fifth and sixth arguments to
recvfrom and sendto.
• msg_name points to a socket address structure in which the caller stores the destination's
protocol address for sendmsg, or in which recvmsg stores the sender's protocol address.
• If a protocol address does not need to be specified (e.g., a TCP socket or a connected UDP
socket), msg_name should be set to a null pointer.
• The msg_iov and msg_iovlen members specify the array of input or output buffers,
similar to the second and third arguments for readv or writev.
• The msg_control and msg_controllen members specify the location and size of the
optional ancillary data. msg_controllen is a value-result argument for recvmsg.
• The msg_flags member is used only by recvmsg. The msg_flags member is ignored by
sendmsg.
• Summary of input and output
flags by various I/O functions

10
Data structures when recvmsg is called for a UDP
socket

11
msghdr When recvmsg Returns
• A 170-byte UDP datagram arrives from 192.6.38.100, port 2000, destined for our UDP
socket with a destination IP address of 206.168.112.96.
• The shaded fields are modified by recvmsg

12
Comparison of Five Groups of
I/O Functions

13
Ancillary Data
• Ancillary data can be sent and received using the msg_control and msg_controllen
members of the msghdr structure with the sendmsg and recvmsg functions.
• Another term for ancillary data is control information.
• Ancillary data consists of one or more ancillary data objects, each one beginning with a
cmsghdr structure, defined by including <sys/socket.h>.
• struct cmsghdr {
socklen_t cmsg_len; /* length in bytes, including this structure */
int cmsg_level; /* originating protocol */
int cmsg_type; /* protocol-specific type */
/* followed by unsigned char cmsg_data[] */
};

14

You might also like