Week 11 #
Multiplexing Input and Output #
Handling multiple input/output clients with
selectandepoll
select
#
int select(int n, fd_set *read_fds, fd_set *write_fds, NULL, struct timeval *wait_timeout);
- Blocks until fds are ready
- Returns 0 if reaches the timeout, else returns positive count if some fds are ready
- Modifies the given
fd_sets, set them again before the next call fd_set: holds a set of file descriptorsn: The highest fd you specify, + 1
fd_set functions
#
void FD_ZERO(fd_set *s); // empties the set
void FD_SET(int fd, fd_set *s); // adds an fd to the set
void FD_CLR(int fd, fd_set *s); // deletes an fd
int FD_ISSET(int fd, fd_set *s); // queries if fd is in the set
Limitations #
- Max size for
fd_setusually 1024 - Slow when using many file descriptors
epoll
#
Only available on Linux
int epoll_create1(int flags);
- Creates a new
epollinstance - Returns the file descriptor of this instance (
epfd) flags: 0 orFD_CLOEXEC- Instance only useful for other
epollfunctions
int epol_ctl(int epfd, int op, int another_epfd, struct epoll_event *ev);
- Sets what the
epollinstance will wait for - Returns 0 if successful
op:EPOLL_CTL_ADD,EPOLL_CTL_DEL,EPOLL_CTL_MODev: Events to wait for
int epoll_wait(int epfd, struct epoll_event *evs, int n, int timeout);
evs: Array to recieve eventsn: Length of events array- Returns count of ready file descriptors
struct epoll_event {
uint32_t events;
epoll_data_t data;
};
You can combine
eventsusing bitwise operatorsevents:EPOLLIN: Ready to readEPOLLOUT: Ready to writeEPOLLONESHOT: Monitor once onlyEPOLLET: Notify whenever changes from not-ready to readyEPOLLHUP: Other end of pipe/socket has closedEPOLLERR: Error condition
typedef union epoll_data {
void *ptr;
int fd;
uint32_t u32;
uint64_t u64;
} epoll_data_t;
- You store to this data when calling
epoll_ctl - Stored data gets returned when you call
epoll_wait - Usually store the fd, or a pointer to some
structto keep track of history