• linkedu视频
  • 平面设计
  • 电脑入门
  • 操作系统
  • 办公应用
  • 电脑硬件
  • 动画设计
  • 3D设计
  • 网页设计
  • CAD设计
  • 影音处理
  • 数据库
  • 程序设计
  • 认证考试
  • 信息管理
  • 信息安全
菜单
linkedu.com
  • 网页制作
  • 数据库
  • 程序设计
  • 操作系统
  • CMS教程
  • 游戏攻略
  • 脚本语言
  • 平面设计
  • 软件教程
  • 网络安全
  • 电脑知识
  • 服务器
  • 视频教程
  • JavaScript
  • ASP.NET
  • PHP
  • 正则表达式
  • AJAX
  • JSP
  • ASP
  • Flex
  • XML
  • 编程技巧
  • Android
  • swift
  • C#教程
  • vb
  • vb.net
  • C语言
  • Java
  • Delphi
  • 易语言
  • vc/mfc
  • 嵌入式开发
  • 游戏开发
  • ios
  • 编程问答
  • 汇编语言
  • 微信小程序
  • 数据结构
  • OpenGL
  • 架构设计
  • qt
  • 微信公众号
您的位置:首页 > 程序设计 >Android > Linux I/O多路复用

Linux I/O多路复用

作者:网友 字体:[增加 减小] 来源:互联网 时间:2017-05-26

网友通过本文主要向大家介绍了linux多路复用,linux 多路输入输出,i/o多路复用,什么是i/o多路复用,多路复用等相关知识,希望对您有所帮助,也希望大家支持linkedu.com www.linkedu.com

Linux I/O多路复用


Linux I/O多路复用

1 I/O多路复用

I/O多路复用通过一种机制,可以监视多个描述符,一旦某个描述符就绪(一般是读就绪或者写就绪),能够通知程序进行相应的读写操作。

I/O 多路复用技术是为了解决进程或线程阻塞到某个I/O系统调用而出现的技术,使进程不阻塞于某个特定的 I/O 系统调用。

2 I/O多路复用select

该函数准许进程指示内核等待多个事件中的任何一个发送,并只在有一个或多个事件发生或经历一段指定的时间后才唤醒。

2.1 select函数

2.1.1 需要头文件

#include

#include

#include

#include

2.1.2 声明和返回值

1 声明

int select(int nfds,fd_set *readfds, fd_set *writefds, fd_set *exceptfds, struct timeval *timeout);

2返回值

成功:就绪描述符的数目,超时返回 0。

出错:-1。

2.1.3 功能

监视并等待多个文件描述符的属性变化(可读、可写或错误异常)。select()函数监视的文件描述符分 3 类,分别是writefds、readfds、和exceptfds。调用后select() 函数会阻塞,直到有描述符就绪(有数据可读、可写、或者有错误异常),或者超时( timeout 指定等待时间),函数才返回。当select()函数返回后,可以通过遍历 fdset,来找到就绪的描述符。

2.1.4 参数

1nfds: 要监视的文件描述符的范围,一般取监视的描述符数的最大值+1,如这里写 10,这样的话,描述符 0,1, 2 …… 9 都会被监视,在 Linux 上最大值一般为1024。

2readfd: 监视的可读描述符集合,只要有文件描述符即将进行读操作,这个文件描述符就存储到这。

3writefds: 监视的可写描述符集合。

4exceptfds: 监视的错误异常描述符集合。

5timeout告知内核等待所指定描述字中的任何一个就绪可花多少时间。 其timeval结构用于指定这段时间的秒数和微秒数。

struct timeval{

long tv_sec; //seconds

long tv_usec; //microseconds

};

timeout可以设置的值:

1、把该参数设置为空指针NULL。表示永远等待下去,当有一个描述字准备好I/O时才返回。

2、把该参数设置为指定了timeval结构中的秒数和微秒数的值。表示等待指定了超时时间,当超时后还没有描述字准备好I/O时直接返回。

3、把该参数设置为指定了timeval结构中的秒数和微秒数的值,而且秒数和微秒都为0。表示不检查描述字是否准备好I/O后立即返回,这称为轮询。

2.1.5 fd_set

fd_set可以理解为一个集合,这个集合中存放的是文件描述符,可通过以下四个宏进行设置:

1void FD_ZERO(fd_set *fdset);//清空集合

2void FD_SET(int fd, fd_set *fdset);//将一个给定的文件描述符加入集合之中

3void FD_CLR(int fd, fd_set *fdset);//将一个给定的文件描述符从集合中删除

4int FD_ISSET(int fd, fd_set *fdset);//检查集合中指定的文件描述符是否可以读写

2.3 select优点和缺点

2.3.1 优点

select()目前几乎在所有的平台上支持,其良好跨平台支持也是它的一个优点。

2.3.2 缺点

1、每次调用 select(),都需要把fd集合从用户态拷贝到内核态,这个开销在fd很多时会很大,同时每次调用select()都需要在内核遍历传递进来的所有fd,这个开销在fd很多时也很大。

2、单个进程能够监视的文件描述符的数量存在最大限制,在Linux上一般为1024,可以通过修改宏定义甚至重新编译内核的方式提升这一限制,但是这样也会造成效率的降低。

3 I/O多路复用poll

select()和poll()系统调用的本质一样,前者在BSD UNIX中引入的,后者在System V中引入的。poll()的机制与 select() 类似,与 select() 在本质上没有多大差别,管理多个描述符也是进行轮询,根据描述符的状态进行处理,但是 poll() 没有最大文件描述符数量的限制(但是数量过大后性能也是会下降)。poll() 和 select() 同样存在一个缺点就是,包含大量文件描述符的数组被整体复制于用户态和内核的地址空间之间,而不论这些文件描述符是否就绪,它的开销随着文件描述符数量的增加而线性增大。

3.1 poll函数

3.1.1 需要头文件

#include

3.1.2 声明和返回值

1声明

intpoll(struct pollfd *fds, nfds_t nfds, int timeout);

2返回值

成功时,poll()返回结构体中revents域不为0的文件描述符个数;如果在超时前没有任何事件发生,poll()返回 0;

失败时,poll()返回 -1,并设置 errno 为下列值之一:

EBADF:一个或多个结构体中指定的文件描述符无效。

EFAULT:fds 指针指向的地址超出进程的地址空间。

EINTR:请求的事件之前产生一个信号,调用可以重新发起。

EINVAL:nfds参数超出 PLIMIT_NOFILE 值。

ENOMEM:可用内存不足,无法完成请求。

3.1.3 功能

监视并等待多个文件描述符的属性变化。

3.1.4 参数

1fds 不同与select()使用三个位图来表示三个 fdset 的方式,poll()使用一个pollfd的指针实现。一个pollfd 结构体数组,其中包括了你想测试的文件描述符和事件, 事件由结构中事件域 events 来确定,调用后实际发生的时间将被填写在结构体的revents 域。

struct pollfd{

int fd; //文件描述符

short events; //等待的事件

short revents; //实际发生了的事件

};

fd 每一个 pollfd 结构体指定了一个被监视的文件描述符,可以传递多个结构体,指示poll()监视多个文件描述符。

events:每个结构体的 events 域是监视该文件描述符的事件掩码,由用户来设置这个域。events 等待事件的掩码取值如下:

处理输入:

POLLIN 普通或优先级带数据可读

POLLRDNORM 普通数据可读

POLLRDBAND 优先级带数据可读

POLLPRI 高优先级数据可读

处理输出:

POLLOUT 普通或优先级带数据可写

POLLWRNORM 普通数据可写

POLLWRBAND 优先级带数据可写

处理错误:

POLLERR发生错误

POLLHUP发生挂起

POLLVAL 描述字不是一个打开的文件

poll() 处理三个级别的数据,普通normal,优先级带priority band,高优先级high priority,这些都是出于流的实现。

POLLIN | POLLPRI 等价于select()的读事件。

POLLOUT | POLLWRBAND等价于select() 的写事件。

POLLIN等价于POLLRDNORM | POLLRDBAND。

POLLOUT等价于POLLWRNORM。

例如,要同时监视一个文件描述符是否可读和可写,我们可以设置events为 POLLIN | POLLOUT。

revents域是文件描述符的操作结果事件掩码,内核在调用返回时设置这个域。events 域中请求的任何事件都可能在revents域中返回。每个结构体的 events 域是由用户来设置,告诉内核我们关注的是什么,而revents域是返回时内核设置的,以说明对该描述符发生了什么事件。

2nfds 用来指定第一个参数数组元素个数。

分享到:QQ空间新浪微博腾讯微博微信百度贴吧QQ好友复制网址打印

您可能想查找下面的文章:

  • Linux I/O多路复用

相关文章

  • 2017-05-26硅谷社交2--欢迎页面,硅谷社交2--
  • 2017-05-26自动化运维之cobbler批量部署操作系统(一)
  • 2017-05-26linux下神奇的script命令
  • 2017-05-26Form and Control KeyEvent
  • 2017-05-26ArcGIS for Android地图控件的5大常见操作转,arcgisandroid
  • 2017-05-26Android中的Service,AndroidService
  • 2017-05-26Android电池电量跳变,android电池电量
  • 2017-05-26配置Nginx反向代理Exchange 2007上的OWA
  • 2017-05-26硅谷新闻5--顶部新闻轮播图事件处理,硅谷5--
  • 2017-05-26android NDK 教程一(初识JNI--hello world)

文章分类

  • JavaScript
  • ASP.NET
  • PHP
  • 正则表达式
  • AJAX
  • JSP
  • ASP
  • Flex
  • XML
  • 编程技巧
  • Android
  • swift
  • C#教程
  • vb
  • vb.net
  • C语言
  • Java
  • Delphi
  • 易语言
  • vc/mfc
  • 嵌入式开发
  • 游戏开发
  • ios
  • 编程问答
  • 汇编语言
  • 微信小程序
  • 数据结构
  • OpenGL
  • 架构设计
  • qt
  • 微信公众号

最近更新的内容

    • Android开发6:Service的使用(简单音乐播放器的实现),androidservice
    • 如何使用Android Studio开发Gradle插件
    • 安卓蓝牙技术Bluetooth使用流程(Bluetooth详解),安卓bluetooth
    • ELK部署参考文档
    • 美女的秘密项目源码,美女秘密项目源码
    • 8.3.10 Paint API之—— ColorFilter(颜色过滤器)(2-3)
    • android开发之路05,android之路05
    • Setting 之dashboard 点击跳转流程,settingdashboard
    • Android之ContentProvider数据存储,contentprovider
    • 2.5.6 ViewFlipper(翻转视图)的基本使用

关于我们 - 联系我们 - 免责声明 - 网站地图

©2020-2025 All Rights Reserved. linkedu.com 版权所有