linux系统编程——文件IO——事件轮询接口
2021/8/24 7:07:47
本文主要是介绍linux系统编程——文件IO——事件轮询接口,对大家解决编程问题具有一定的参考价值,需要的程序猿们随着小编来一起学习吧!
1. 为什么需要epoll
select和poll的特点是:用户给内核一张 需要查看的文件描述符表,内核必须处理表中的每一个文件描述符,当这个表变大时,程序性能降低。
epoll将事件监视器的注册和事件监视工作分离,以避开这个问题。
2. api
// @size : 用于提示内核要监控的文件描述符数目,并非最大数目,用于提升性能 int epoll_create(int size); int epoll_create1(int flags); int epoll_ctl(int epfd, int op, int fd, struct epoll_event *event); typedef union epoll_data { void *ptr; int fd; uint32_t u32; uint64_t u64; } epoll_data_t; struct epoll_event { uint32_t events; /* Epoll events */ epoll_data_t data; /* User data variable */ }; int epoll_wait(int epfd, struct epoll_event *events, int maxevents, int timeout);
#define MAX_EVENTS 10 struct epoll_event ev, events[MAX_EVENTS]; int listen_sock, conn_sock, nfds, epollfd; /* Code to set up listening socket, 'listen_sock', (socket(), bind(), listen()) omitted */ epollfd = epoll_create1(0); if (epollfd == -1) { perror("epoll_create1"); exit(EXIT_FAILURE); } ev.events = EPOLLIN; ev.data.fd = listen_sock; if (epoll_ctl(epollfd, EPOLL_CTL_ADD, listen_sock, &ev) == -1) { perror("epoll_ctl: listen_sock"); exit(EXIT_FAILURE); } for (;;) { nfds = epoll_wait(epollfd, events, MAX_EVENTS, -1); if (nfds == -1) { perror("epoll_wait"); exit(EXIT_FAILURE); } for (n = 0; n < nfds; ++n) { if (events[n].data.fd == listen_sock) { conn_sock = accept(listen_sock, (struct sockaddr *) &addr, &addrlen); if (conn_sock == -1) { perror("accept"); exit(EXIT_FAILURE); } setnonblocking(conn_sock); ev.events = EPOLLIN | EPOLLET; ev.data.fd = conn_sock; if (epoll_ctl(epollfd, EPOLL_CTL_ADD, conn_sock, &ev) == -1) { perror("epoll_ctl: conn_sock"); exit(EXIT_FAILURE); } } else { do_use_fd(events[n].data.fd); } } }
3. 边缘触发和水平触发
若将epoll_ctl 的 event.events 设置为 EPOLLET,则使用边缘触发。
比如,如下事件
- 生产者将1KB数据写入管道
- 消费者对管道调用epoll_wait,等待管道送来数据并因此而读取。
若使用水平触发,则在调用2立即返回,表示读管道不会阻塞。
若使用边缘触发,则在调用1发生返回,说明 即使 管道已经可读,但epoll_wait也不会返回,除非再次发生写管道事件。
水平触发是默认行为,边缘触发需要使用不同的程序设计方法,通常用于非阻挡IO并且仔细检测EAGAIN.
这篇关于linux系统编程——文件IO——事件轮询接口的文章就介绍到这儿,希望我们推荐的文章对大家有所帮助,也希望大家多多支持为之网!
- 2024-12-18git仓库有更新,jenkins 自动触发拉代码怎么配置的?-icode9专业技术文章分享
- 2024-12-18Jenkins webhook 方式怎么配置指定的分支?-icode9专业技术文章分享
- 2024-12-13Linux C++项目实战入门教程
- 2024-12-13Linux C++编程项目实战入门教程
- 2024-12-11Linux部署Scrapy教程:新手入门指南
- 2024-12-11怎么将在本地创建的 Maven 仓库迁移到 Linux 服务器上?-icode9专业技术文章分享
- 2024-12-10Linux常用命令
- 2024-12-06谁看谁服! Linux 创始人对于进程和线程的理解是…
- 2024-12-04操作系统教程:新手入门及初级技巧详解
- 2024-12-04操作系统入门:新手必学指南