I/O多路复用---select

常见的linux服务器类型

1.多进程并发服务器

2.多线程并发服务器

3.select多路I/O转接服务器

4.poll多路I/O转接服务器

5.epoll多路I/O转接服务器

多路IO是指单个线程通过记录跟踪每一个 IO流的状态同时来管理多个IO流,尽量提高服务器的吞吐量

与多进程多线程相比IO多路复用的计数最大优势就是系统开销小,不必创建进程/线程,也不必维护 进程/线程

IO多路复用使用场景

(1)当客户处理多个描述符时(一般是交互式输入或网络套接口)

(2)当一个客户同时处理多个套接口时

(3)如果一个TCP服务器即要处理监听套接口又要处理UDP一般使用IO复用

(4)如果一个服务器要处理多个服务或协议

select,poll,epoll都是多路复用的机制。所谓的多路复用机制就是通过一种机制可以监视多个文件描述符,一旦某个文件描述符就绪(一般是读就绪或者写就绪),能够通知程序进行相应的读写操作,但是select,poll,epoll本质上都是同步IOd因为他们都需要在读写事件就绪后自己负责进行读写,也就是说读写过程是阻塞的,而异步IO无需自己负责读写,异步IO的实现会负责把数据从内核拷贝到用户控件

1.函数参数

int select(int nfds, fd_set* readfds, fd_set* writefds, fd_set* execptfds, struct timeval* timmeout);

nfds:监控的文件描述符集里最大的文件描述符加1

readfds:监控有读数据到达文件描述符集合,传入传出参数

writefds:监控有写数据到达文件描述符集合,传入传出参数

execptfds:监控异常发生文件描述符集合

timeout:设置阻塞监控呢时间

NULL:永远等下去

timeval:等待固定的时间

timeval里时间均为 0,检查描述符字后立即返回,轮询

void FD_ZERO(fd_set* set);把文件描述符集合里初始化0

void FD_SET(int fd,fd_set* set);把文件描述符里fd位置 置1

void FD_CLR(int fd,fd_set* set);把文件描述 符里fd位置 置0

int FD_ISSET(int fd,fd_set* set);测试文件描述符集合里的fd是否为1,有1返回1,没1返回0

2.函数返回值

执行成功返回文件描述词状态已改变的个数

如果返回 0表示词状态改变前已经超过指定 时间,没有返回

当发生错误时返回-1,错误原因可能是errno,此时参数readfds,writefds,exceptfds和timeout的值变得不可预测

错误的值可能为

EBADF;文件描述词无效或该文件已经关闭

EINTR:此调用被信号中断

EINVAL:参数为负值

ENOMEN:核心内存不足

3.函数模型

理解select模型的关键在于理解fd_set,通常fd_set长度为1字节,fd_set中每一个bit可以对应一个文件描述符fd,则一字节长的fd_set可以对应8个fd

(1)执行fd_set set:FD_ZERO(&set)则set用位表示为0000 0000

(2)若fd=5,执行FD_SET(fd,&set)后set变为 0001,0000(第5位置1)

(3)若再加 fd=2,fd=1则set会变为0001,0011

(4)执行select(6,&set,0,0,0)阻塞等待

(5)执行fd=1,fd=2都发生 可读事件则select返回,此时 set变为0000,0011没有事件发生的fd=5被清空

基于以上特点有以下总结:

(1)可控文件描述符的个数取决于sizeof(fd_set)的值

(2)将fd加入select监控集时还要再使用一个数组保存放到监控集中的fd,一是用于返回后arr作为源数据和fd_set进行判断,二是select返回后会把以前加入的但并无事件发生的fd清空,每次开始select之前都要进行重新从arr取得Fd逐一加入,扫描arr的同时取得fd罪的的maxfd,用于作为select的第一个参数

(3)所以select模型 必须在 select前循环arr(加fd,取maxfd),select返回后循环arr(FD_ISSET判断是否有事件发生)

4.select的缺点

(1)每次调用都需要把fd从用户态拷贝到内核态,这个开销在fd很多时会很大

(2)每次调用select都需要在内核遍历传进来的所有fd,这个开销也很大

(3)select支持的文件描述符太小 ,默认 只有1024

(4)select会修改函数传入的参数数组,当这个函数 被调用很多次的时候就会发生错误

(5)

实现过程

(1)创建监听套接字

(2)设置端口复用 127.0.0.1

指定族:IPv4

指定端口号并转化为网络字节序列

指定Ip并转化为网络字节序列

(3)绑定到监听套接字

(4)将客户端数组 全部初始化为 -1

(5)监听描述集初始化,并将监听套接字加到监听集

(6)如果客户端有链接 请求,则将链接请求添加到监听集合里,然后判断下标i的是否大于当前文件描述符,每次都求取最大的文件描述符 ,一次轮询,当数组 满了的时候关闭当前客户端请求

时间: 2024-10-01 00:28:54

I/O多路复用---select的相关文章

I/O多路复用 SELECT POLL -- 内核实现

等待队列 先补充个基础知识――等待队列 认识 定义 wait_queue_head_t wait_queue; 初始化 init_waitqueue_head(&wait_queue); 等待 wait_event(queue, condition)   等待某个条件而进入睡眠 wait_event_interruptible(queue, condition)  等待某个条件而进入睡眠并允许信号中断睡眠 wait_event_timeout(queue, condition,timeout)

I/O多路复用select/poll/epoll

前言 早期操作系统通常将进程中可创建的线程数限制在一个较低的阈值,大约几百个.因此, 操作系统会提供一些高效的方法来实现多路IO,例如Unix的select和poll.现代操作系统中,线程数已经得到了极大的提升,如NPTL线程软件包可支持数十万的线程. I/O多路复用 select select 允许进程指示内核等待多个事件中的任何一个发生,并只在有一个或多个事件发生或指定时间后返回它. select函数原型 #include <sys/select.h> #include <sys/t

非阻塞io模型和io多路复用----select

一.四种io阻塞1.io阻塞:(1 等待数据处于阻塞状态(2从内核copy到用户态处于阻塞状态2.非io阻塞只有从内核copy到用户态处于阻塞状态3.io多路复用----->优势:可以同时监听多个对象(1从check----->ready 通过selec函数来做,处于阻塞状态(2从内核copy到用户态处于阻塞状态3.异步io不用阻塞二.io多路复用select  poll epoll 都属于io同步里面的io多路复用select:轮询问题,监听数量有限poll:提高了监听数量epoll:解决了

IO多路复用——select

IO多路复用 是同步IO的一种,用一个进程一次等待多个IO就绪事件的发生,加大概率,尽可能高效的等. 适用场景 (1)当客户处理多个描述字时(一般是交互式输入和网络套接口),必须使用I/O复用. (2)当一个客户同时处理多个套接口时,而这种情况是可能的,但很少出现. (3)如果一个TCP服务器既要处理监听套接口,又要处理已连接套接口,一般也要用到I/O复用. (4)如果一个服务器即要处理TCP,又要处理UDP,一般要使用I/O复用. (5)如果一个服务器要处理多个服务或多个协议,一般要使用I/O

python IO 多路复用 select poll epoll

三个多路复用模型的概念 select select 原理 select 是通过系统调用来监视着一个由多个文件描述符(file descriptor)组成的数组,当select()返回后,数组中就绪的文件描述符会被内核修改标记位(其实就是一个整数),使得进程可以获得这些文件描述符从而进行后续的读写操作.select饰通过遍历来监视整个数组的,而且每次遍历都是线性的. select 优点 select目前几乎在所有的平台上支持,良好跨平台性. select 缺点 每次调用select,都需要把fd集

IO多路复用-select

首先列一下,sellect.poll.epoll三者的区别 select select最早于1983年出现在4.2BSD中,它通过一个select()系统调用来监视多个文件描述符的数组,当select()返回后,该数组中就绪的文件描述符便会被内核修改标志位,使得进程可以获得这些文件描述符从而进行后续的读写操作. select目前几乎在所有的平台上支持,其良好跨平台支持也是它的一个优点,事实上从现在看来,这也是它所剩不多的优点之一. select的一个缺点在于单个进程能够监视的文件描述符的数量存在

转一贴,今天实在写累了,也看累了--【Python异步非阻塞IO多路复用Select/Poll/Epoll使用】

下面这篇,原理理解了, 再结合 这一周来的心得体会,整个框架就差不多了... http://www.haiyun.me/archives/1056.html 有许多封装好的异步非阻塞IO多路复用框架,底层在linux基于最新的epoll实现,为了更好的使用,了解其底层原理还是有必要的.下面记录下分别基于Select/Poll/Epoll的echo server实现.Python Select Server,可监控事件数量有限制: 1 2 3 4 5 6 7 8 9 10 11 12 13 14

I/O多路复用——select

系统提供select函数来实现多路复用I/O模型,select系统调用是用来让我们的程序监视多个文件句柄的状态变化的.程序会停在select这里等待,直到被监视的文件句柄有一个或多个发生了状态改变. select API: 1)nfds参数指定被监听的文件描述符的总数.它通常被设置为select监听的所有文件描述符中的最大值加1,因为文件描述符是从0开始计数的. 2)readfds.writefds和exceptfds参数都是输入输出型参数,分别指向可读.可写和异常等事件对应的文件描述符集合.作

多路复用select和epoll的区别(转)

先说下本文框架,先是问题引出,然后概括两个机制的区别和联系,最后介绍每个接口的用法 一.问题引出 联系区别 问题的引出,当需要读两个以上的I/O的时候,如果使用阻塞式的I/O,那么可能长时间的阻塞在一个描述符上面,另外的描述符虽然有数据但是不能读出来,这样实时性不能满足要求,大概的解决方案有以下几种: 1.使用多进程或者多线程,但是这种方法会造成程序的复杂,而且对与进程与线程的创建维护也需要很多的开销.(Apache服务器是用的子进程的方式,优点可以隔离用户) 2.用一个进程,但是使用非阻塞的I

多路复用select

多路复用I/O:一个执行体监视多个文件描述符对象的状态是否改变,一旦改变通知其他执行体来实现. 基本思想: 1. 先构造一张有关描述符的表,然后调用一个函数,当这些文件描述符中的一个或者多个已准备好进行I/O时函数才返回 2. 函数返回时告诉进程那个描述符已准备就绪,可以进行I/O操作. Select(int n,fd_set *read_fds,fd_set *write_fds,fd_set *except_fds,struct timeval *timeout); 注意两点: 1. sel