Sei sulla pagina 1di 20

I/O Multiplexing

What is I/O multiplexing?


When an application needs to handle multiple I/O descriptors at the same time
E.g. file and socket descriptors, multiple socket descriptors

When I/O on any one descriptor can result in blocking

Non-forking concurrent server


Concurrent Server
select()
listenfd

Sockets

fd1

fd2

fd3

fd4

fd5

Clients C1

C2

C3

C4

C5

I/O Models
1. 2. 3. 4. 5. Blocking I/O Non-blocking I/O I/O multiplexing select() Signal driven I/O Asynchronous I/O

Blocking I/O
Application recvfrom() System call Operating system No datagram ready

Wait for data


Process blocks

datagram ready Copy datagram


Copy data to user

Process datagram

Return ok

Copy complete

Non-Blocking I/O
Application recvfrom() recvfrom() recvfrom() System call
EWOULDBLOCK

Operating system No datagram ready No datagram ready datagram ready Copy datagram
Copy data to user

System call
EWOULDBLOCK

System call

Process blocks

Process datagram

Return ok

Copy complete

I/O Multiplexing
Application select()
Process blocks Return readable

Operating system System call No datagram ready

Wait for data


datagram ready Copy datagram
Copy data to user

recvfrom()
Process blocks

System call

Process datagram

Return ok

Copy complete

Signal driven I/O


Application
Establish SIGIO Signal handler Process continues Deliver SIGIO

Operating system System call No datagram ready

Wait for data


datagram ready Copy datagram
Copy data to user

Signal Handler

recvfrom()
Process blocks

System call

Process datagram

Return ok

Copy complete

Asynchronous I/O
Application aio_read() System call return Operating system No datagram ready

Wait for data


Process continues

datagram ready Copy datagram


Copy data to user

Signal handler Process datagram

Return ok

Copy complete

select() call
Allows a process to wait for an event to occur on any one of its descriptors.
Types of event
ready for read ready for write Exception condition

select() call
int select( int maxfdp1, /* fd_set *readfds, /* fd_set *writefds, /* fd_set *exceptfds, /* struct timeval *timeout);
max. fd + 1 */ read ready? */ write ready? */ exceptions? */

struct timeval { long tv_sec; /* seconds */ long tv_usec; /* microseconds */ }

struct fd_set
Set of descriptors that we want to wait on for events.
Typically holds 256 descriptor states. Manipulation macros
void void void void FD_ZERO(fd_set *fds) FD_SET (int fd, fd_set *fds) FD_CLR (int fd, fd_set *fds) FD_ISSET(int fd, fd_set *fds)

Non-forking Concurrent Server


fdset rdset, wrset; int listenfd, connfd1, connfd2; int maxfdp1; Connection establishment etc. /* initialize */ FD_ZERO(&rdset); FD_ZERO(&wrset);

for( ;; ) { FD_SET(connfd1, &rdset); FD_SET(connfd2, &wrset); FD_SET(listenfd, &rdset); maxfdp1 = max(connfd1, connfd2, listenfd) + 1; /* wait for some event */ Select(maxfdp1, &rdset, &wrset, NULL, NULL); if( FD_ISSET(connfd1, &rdset) ) {
Read data from connfd1

} if( FD_ISSET(connfd2, &wrset) ) {


Write data to connfd2

} if( FD_ISSET(listenfd, &rdset) {


Process a new connection

} }

High resolution timer!


Select can be used as a millisecond resolution timer.
select ( 0, NULL, NULL, NULL, &timeval) Usual sleep() call has resolution of seconds.

Socket Options

Managing socket options 3 ways


getsockopt() and setsockopt() fcntl() ioctl()

getsockopt() and setsockopt()


int getsockopt( int sockfd, int level, /* SOL_SOCKET, IPPROTO_IP, IPPROTO_TCP etc */ int optname, /* option name */ void *optval, /* option value */ socklen_t *optlen); /* data length of option*/
int setsockopt( int sockfd, int level, int optname, const void *optval, socklen_t optlen);

Some socket options


SO_BROADCAST - enable socket for sending broadcast SO_KEEPALIVE regularly probes on inactive TCP connection.

SO_LINGER linger till all data is sent before returning from close() on a TCP connection.
SO_RCVBUF/ SO_SNDBUF size of receive/send buffers on socket. SO_RCVTIMEO/SO_SNDTIMEO place timeout on receive/send operation.

fcntl()
int fcntl(int fd, int cmd, long arg);
Miscellaneous file control operations
Non-blocking I/O (O_NONBLOCK, F_SETFL) Signal-driven I/O (O_ASYNC, F_SETFL) Set socket owner (F_SETOWN)

Potrebbero piacerti anche