函数select、poll
函数select
select函数:
int select(int nfds, fd_set *readfds, fd_set *writefds, fd_set *exceptfds, struct timeval *timeout);
参数:
- nfds:监控的文件描述符集里最大文件描述符加1,因为此参数会告诉内核检测前多少个文件文件描述符
- readfs:监控有读数据到达文件描述符集合,传入传出参数
- writefds:监控写数据到达文件描述符集合,传入传出参数
- exceptfds:监控异常发生到达文件描述符集合,如带外数据到达异常,传入传出参数
- timeout:定时阻塞监控时间。
void FD_CLR(int fd, fd_set *set); // 把文件描述符集里fd位清0
int FD_ISSET(int fd, fd_set *set); // 测试文件描述符集里fd是否置1
void FD_SET(int fd, fd_set *set); // 把文件描述符集合里fd位置1
void FD_ZERO(fd_set *set); // 把文件描述符集合里所有位清0
1. 测试代码:
- 服务端
//server.c
#include <unistd.h>
#include <stdio.h>
#include <string.h>
#include <netinet/in.h>
#include <arpa/inet.h>
#include <signal.h>
#include <sys/wait.h>
#include <ctype.h>
#include <unistd.h>
#include <sys/select.h>
#include "wrap.h" #define SERV_PROT 6666 int main(int argc, char *argv[])
{
int i, j, n, nread; int maxfd = ;
int listenfd, connfd;
char buf[BUFSIZ]; struct sockaddr_in clie_addr, serv_addr;
socklen_t clie_addr_len;
listenfd = Socket(AF_INET, SOCK_STREAM, ); int opt = ;
setsockopt(listenfd, SOL_SOCKET, SO_REUSEADDR, &opt, sizeof(opt)); bzero(&serv_addr, sizeof(serv_addr));
serv_addr.sin_family = AF_INET;
serv_addr.sin_addr.s_addr = htonl(INADDR_ANY);
serv_addr.sin_port = htons(SERV_PROT);
Bind(listen, (struct sockaddr*)&serv_addr, sizeof(serv_addr));
Listen(listenfd, ); fd_set rset, allset;
maxfd = listenfd;
FD_ZERO(&allset);
FD_SET(listenfd, &allset);
while ()
{
rset = allset;
nread = select(maxfd + , &rset, NULL, NULL, NULL); //每次循环都从新设置select监控信号集
if(nread < )
perr_exit("select error"); if (FD_ISSET(listenfd, &rset)) //说明有新的客户端连接请求
{
clie_addr_len = sizeof(clie_addr);
connfd = Accept(listenfd, (struct sockaddr *)&clie_addr, &clie_addr_len); FD_SET(connfd, &allset); //向监控文件描述符集合allset添加新的文件描述符connfd if (maxfd < connfd)
maxfd = connfd; if ( == --nread) //说明select只返回一个,并且listenfd,后续执行无须执行
continue;
}
for (i = listenfd + ; i <= maxfd; i++)
{
if (FD_ISSET(i, &rset))
{
if ((n = Read(i, buf, sizeof(buf))) == ) //当client关闭链接时, 服务端也关闭对应链接
{
Close(i);
FD_CLR(i, &allset); //解除select对此文件描述符的监控
}
else if(n == -)
perr_exit("read error");
for (j = ; j < n; ++j)
buf[j] = toupper(buf[j]);
Write(i, buf, n);
}
}
}
Close(listenfd);
return ;
}
- 客户端
//client.c
#include <arpa/inet.h>
#include "wrap.h" #define SERV_IP "192.168.245.139"
#define SERV_PORT 6666 int main(void)
{
int sfd, len;
struct sockaddr_in serv_addr;
char buf[BUFSIZ];
sfd = Socket(AF_INET, SOCK_STREAM, );
bzero(&serv_addr, sizeof(serv_addr));
serv_addr.sin_family = AF_INET;
inet_pton(AF_INET, SERV_IP, &serv_addr.sin_addr.s_addr);
serv_addr.sin_port = htons(SERV_PORT);
Connect(sfd, (struct sockaddr *)&serv_addr, sizeof(serv_addr)); while ()
{
fgets(buf, sizeof(buf), stdin);
int r = Write(sfd, buf, strlen(buf));
printf("Write r ======== %d\n", r);
len = Read(sfd, buf, sizeof(buf));
printf("Read len ========= %d\n", len);
Write(STDOUT_FILENO, buf, len);
}
Close(sfd);
return ;
}
代码下载地址:链接
输出结果:
函数select、poll的更多相关文章
- select()/poll() 的内核实现
mark 引用:http://janfan.cn/chinese/2015/01/05/select-poll-impl-inside-the-kernel.html 文章 select()/poll ...
- 知识联结梳理 : I/O多路复用、EPOLL(SELECT/POLL)、NIO、Event-driven、Reactor模式
为了形成一个完整清晰的认识,将概念和关系梳理出来,把坑填平. I/O多路复用 I/O多路复用主要解决传统I/O单线程阻塞的问题.它通过单线程管理多个FD,当监听的FD有状态变化的时候的,调用回调函数, ...
- Linux下select&poll&epoll的实现原理(一)
最近简单看了一把 linux-3.10.25 kernel中select/poll/epoll这个几个IO事件检测API的实现.此处做一些记录.其基本的原理是相同的,流程如下 先依次调用fd对应的st ...
- Python之路-python(Queue队列、进程、Gevent协程、Select\Poll\Epoll异步IO与事件驱动)
一.进程: 1.语法 2.进程间通讯 3.进程池 二.Gevent协程 三.Select\Poll\Epoll异步IO与事件驱动 一.进程: 1.语法 简单的启动线程语法 def run(name): ...
- 多进程、协程、事件驱动及select poll epoll
目录 -多线程使用场景 -多进程 --简单的一个多进程例子 --进程间数据的交互实现方法 ---通过Queues和Pipe可以实现进程间数据的传递,但是不能实现数据的共享 ---Queues ---P ...
- Python自动化 【第十篇】:Python进阶-多进程/协程/事件驱动与Select\Poll\Epoll异步IO
本节内容: 多进程 协程 事件驱动与Select\Poll\Epoll异步IO 1. 多进程 启动多个进程 进程中启进程 父进程与子进程 进程间通信 不同进程间内存是不共享的,要想实现两个进程间 ...
- select,poll,epoll的归纳总结区分
Select.Poll与Epoll比较 以下资料都是来自网上搜集整理.引用源详见文章末尾. 1 Select.Poll与Epoll简介 Select select本质上是通过设置或者检查存放fd标志位 ...
- [转载] Linux下多路复用IO接口 epoll select poll 的区别
原地址:http://bbs.linuxpk.com/thread-43628-1-1.html 废话不多说,一下是本人学习nginx 的时候总结的一些资料,比较乱,但看完后细细揣摩一下应该就弄明白区 ...
- select poll使用
select poll使用 2.1. 怎样管理多个连接?“我想同一时候监控一个以上的文件描写叙述符(fd)/连接(connection)/流(stream),应该怎么办?” 使用 select ...
随机推荐
- Shell-find . -type f -name "*.jpg" -print | xargs tar -czvf images.tar.gz
查找所有的 jpg 文件,并且压缩它们: find . -type f -name "*.jpg" -print | xargs tar -czvf images.tar.gz
- 华为QUIDWAY系列路由器的负载均衡配置
作者:邓聪聪 华为系列路由器的负载均衡NQA联动侦测配置案例: 需求:该局域网,IP地址(末位奇数)走联通,IP地址(末位偶数)走电信当某个运营商不可达时,自动切换.通过NQA来确定运营商是否可达., ...
- wtforms-表单生成及验证
介绍 wtforms是一个支持多个web框架的form组件,主要用来做表单的验证以及生成的, 安装 pip install wtforms 使用 自定义一个类,继承wtforms.Form类,定义字段 ...
- C++ 三/五法则
当定义一个类时,我们显式地或隐式地指定了此类型的对象在拷贝.赋值和销毁时做什么.一个类通过定义三种特殊的成员函数来控制这些操作:拷贝构造函数.拷贝赋值运算符和析构函数. 拷贝构造函数定义了当用同类型的 ...
- 线性回归,逻辑回归,神经网络,SVM的总结
目录 线性回归,逻辑回归,神经网络,SVM的总结 线性回归,逻辑回归,神经网络,SVM的总结 详细的学习笔记. markdown的公式编辑手册. 回归的含义: 回归就是指根据之前的数据预测一个准确的输 ...
- 关于Mac的rootless问题
由于在OS X 10.11版本添加了rootless,使得root用户在DOS命令下无法操作系统文件并提示无权限. 解决办法: 首先确认升级到最新版本 重新启动电脑,持续按住Command-R直到看见 ...
- 使用openssl命令制作ecc证书
# openssl ecparam -out EccCA.key -name prime256v1 -genkey # openssl req -config openssl.cnf -key Ecc ...
- vue 不常见操作
对 v-html 的扩展操作, 问题产生背景, 在vue 项目中,用v-html渲染 html字符串,这里面包括a 标签等内容,因为某种需求,a 的默认跳转不符合要求,要经过自己定义的方法跳转. 原 ...
- MS SqlServer还原数据库,出现媒体簇的结构不正确
出现此问题,是数据库版本过低导致,只要保证连接实例所在的版本号>=要还原的数据库的版本号,即可还原成功. 可以使用select @@VERSION,查看当前实例版本.
- liunx 安装 mysql 5.6
第一步 解压文件 目录切换到/usr/local/ cd /usr/local/ 解压 tar zxvf mysql-5.6.33-linux-glibc2.5-x86_64.tar.gz 重命名为 ...