0
  • 聊天消息
  • 系统消息
  • 评论与回复
登录后你可以
  • 下载海量资料
  • 学习在线课程
  • 观看技术视频
  • 写文章/发帖/加入社区
会员中心
创作中心

完善资料让更多小伙伴认识你,还能领取20积分哦,立即完善>

3天内不再提示

Linux的5种IO模型

FPGA之家 来源:FPGA之家 作者:FPGA之家 2022-08-12 09:22 次阅读
加入交流群
微信小助手二维码

扫码添加小助手

加入工程师交流群

哈喽,我是老吴,俺又来分享文章啦!

浑浑噩噩到了 30 岁,距离开滴滴还有 5 年的时间。

还有机会全身而退吗?

哈哈!

30 而立,今年会是值得拼搏的一年,干它!

以下是正文:

一、Linux 的 5 种 IO 模型
二、如何使用信号驱动式 I/O?
三、内核何时会发送 "IO 就绪" 信号?
四、最简单的示例
五、扩展知识

一、Linux 的 5 种 IO 模型

阻塞式 I/O:

系统调用可能因为无法立即完成而被操作系统挂起,直到等待的事件发生为止。

1ad5174c-19db-11ed-ba43-dac502259ad0.png

点击查看大图

非阻塞式 I/O (O_NONBLOCK):

系统调用则总是立即返回,而不管事件是否已经发生。

1ae66bb4-19db-11ed-ba43-dac502259ad0.png

点击查看大图

I/O 复用 (select、poll、epoll):

通过 I/O 复用函数向内核注册一组事件,内核通过 I/O 复用函数把其中就绪的事件通知给应用程序。

1af9df32-19db-11ed-ba43-dac502259ad0.png

点击查看大图

信号驱动式 I/O (SIGIO):

为一个目标文件描述符指定宿主进程,当文件描述符上有事件发生时,SIGIO 的信号处理函数将被触发,然后便可对目标文件描述符执行 I/O 操作。

1b1c96da-19db-11ed-ba43-dac502259ad0.png

点击查看大图

异步 I/O (POSIX 的 aio_ 系列函数):

异步 I/O 的读写操作总是立即返回,而不论 I/O 是否是阻塞的,真正的读写操作由内核接管。

1b327766-19db-11ed-ba43-dac502259ad0.png

点击查看大图

思考一下,什么时候应该选择何种 I/O 模型?为何要这么选择?

下面重点关注信号驱动式 I/O 这一模型,其他模型可查阅文末参考书籍。

二、如何使用信号驱动式 I/O?

一般通过如下 6 个步骤来使用信号驱动式 I/O 模型。

1> 为通知信号安装处理函数。

通过 sigaction() 来完成:

intsigaction(intsignum,conststructsigaction*act,structsigaction*oldact);

默认情况下,这个通知信号为 SIGIO。

2> 为文件描述符的设置属主。

通过 fcntl() 的 F_SETOWN 操作来完成:

fcntl(fd,F_SETOWN,pid)

属主是当文件描述符上可执行 I/O 时,会接收到通知信号的进程或进程组。

pid 为正整数时,代表了进程 ID 号。

pid 为负整数时,它的绝对值就代表了进程组 ID 号。

3> 使能非阻塞 I/O。

通过 fcntl() 的 F_SETFL 操作来完成:

flags=fcntl(fd,F_GETFL);
fcntl(fd,F_SETFL,flags|O_NONBLOCK);

4> 使能信号驱动 I/O。

通过 fcntl() 的 F_SETFL 操作来完成:

flags=fcntl(fd,F_GETFL);
fcntl(fd,F_SETFL,flags|O_ASYNC);

5> 进程等待 "IO 就绪" 信号的到来。

当 I/O 操作就绪时,内核会给进程发送一个信号,然后调用在第 1 步中安装好的信号处理函数。

6> 进程尽可能多地执行 I/O 操作。

循环执行 I/O 系统调用直到失败为止,此时错误码为 EAGAIN 或 EWOULDBLOCK。

原因:

信号驱动 I/O 提供的是边缘触发通知,即只有当 I/O 事件发生时我们才会收到通知,

且当文件描述符收到 I/O 事件通知时,并不知道要处理多少 I/O 数据。

三、内核何时会发送 "IO 就绪" 信号?

对于不同类型的文件描述符,情况不一样。

1> 终端

  • 对于终端,当有新的输入时会会产生信号。

2> 管道和 FIFO

对于读端,下列情况会产生信号:

  • 数据写入到管道中;
  • 管道的写端关闭;

对于写端,下列情况会产生信号:

  • 对管道的读操作增加了管道中的空余空间大小。
  • 管道的读端关闭;

3> 套接字

对于 UDP 套接字,下列情况会产生信号:

  • 数据报到达套接字;
  • 套接字上发生异步错误;

对于 TCP 套接字,信号驱动式 I/O 近乎无用。

  • 太多情况都会产生信号,而我们又无法得知事件类型,因此这里就不再列举其产生信号的情况。

四、最简单的示例

信号处理函数:

staticvolatilesig_atomic_tgotSigio=0;

staticvoidhandler(intsig)
{
gotSigio=1;
}

主程序:

intmain(intargc,char*argv[])
{
intflags,j,cnt;
structtermiosorigTermios;
charch;
structsigactionsa;
intdone;

/*Establishhandler*/
sigemptyset(&sa.sa_mask);
sa.sa_flags=SA_RESTART;
sa.sa_handler=handler;
if(sigaction(SIGIO,&sa,NULL)==-1){
perror("sigaction()
");
exit(1);
}

/*Setownerprocess*/
if(fcntl(STDIN_FILENO,F_SETOWN,getpid())==-1){
perror("fcntl()/F_SETOWN
");
exit(1);
}

/*Enable"I/Opossible"signalingandmakeI/Ononblocking*/
flags=fcntl(STDIN_FILENO,F_GETFL);
if(fcntl(STDIN_FILENO,F_SETFL,flags|O_ASYNC|O_NONBLOCK)==-1){
perror("fcntl()/F_SETFL
");
exit(1);
}

for(done=0,cnt=0;!done;cnt++){
sleep(1);

if(gotSigio){
gotSigio=0;

/*Readallavailableinputuntilerror(probablyEAGAIN)
orEOF*/
while(read(STDIN_FILENO,&ch,1)>0&&!done){
printf("cnt=%d;read%c
",cnt,ch);
done=ch=='#';
}
}
}
exit(0);
}

运行效果:

./build/sigio
a
cnt=0;reada
cnt=0;read

abc
cnt=4;reada
cnt=4;readb
cnt=4;readc
cnt=4;read

#
cnt=7;read#

该程序会先使能信号驱动 IO,然后循环执行计数操作。

当有 IO 就绪信号到来时,会去终端读取数据并打印出来,然后继续执行计数操作。

五、扩展知识

I/O 多路复用 、信号驱动 I/O 以及 epoll 机制可用于监视多个文件描述符。

它们并不实际执行 I/O 操作,当某个文件描述符处于就绪态,仍需采用传统的 I/O 系统调用来完成 I/O 操作。

相比 I/O 多路复用,当监视大量的文件描述符时信号驱动 I/O 有着显著的性能优势,原因是内核能够帮进程记录了正在监视的文件描述符列表。

信号驱动 I/O 的缺点:

  • 信号的处理流程较为复杂;

  • 无法指定需要监控的事件类型。

Linux 特有的 epoll 是一个更好的选择。

六、相关参考

UNIX 网络编程卷1

  • 6.2 I/O模型
  • 25 信号驱动式I/O

Linux-UNIX 系统编程手册

  • 63 其他备选的I/O模型

Linux 高性能服务器编程

  • 8.3 I/O 模型

Linux 多线程服务端编程_使用muduo C++网络库

  • 7.4.1 muduo的IO模型

审核编辑 :李倩



声明:本文内容及配图由入驻作者撰写或者入驻合作网站授权转载。文章观点仅代表作者本人,不代表电子发烧友网立场。文章及其配图仅供工程师学习之用,如有内容侵权或者其他违规问题,请联系本站处理。 举报投诉
  • Linux
    +关注

    关注

    88

    文章

    11628

    浏览量

    218013
  • 信号处理
    +关注

    关注

    49

    文章

    1097

    浏览量

    104884
  • 函数
    +关注

    关注

    3

    文章

    4406

    浏览量

    66853

原文标题:思考技术,也思考人生

文章出处:【微信号:zhuyandz,微信公众号:FPGA之家】欢迎添加关注!文章转载请注明出处。

收藏 人收藏
加入交流群
微信小助手二维码

扫码添加小助手

加入工程师交流群

    评论

    相关推荐
    热点推荐

    N32 MCU IO 5V 耐压选型指南

    支持5V耐压IO的MCU能够直接承受5V电压输入,能够增强系统鲁棒性,有效防止意外损坏。01如何快速判断一颗MCU是否支持5V耐压?选型时,无需通读全篇数据手册,只需重点关注以下两处关
    的头像 发表于 11-04 11:31 205次阅读
    N32 MCU  <b class='flag-5'>IO</b> <b class='flag-5'>5</b>V 耐压选型指南

    远程IO不就是分布式IO?其实很多人都理解错了

    一、引言 在工业自动化和控制系统中,分布式io和远程io作为两常见的IO技术,各自具有独特的特点和优势,以下对远程io和分布式
    的头像 发表于 09-28 11:06 428次阅读
    远程<b class='flag-5'>IO</b>不就是分布式<b class='flag-5'>IO</b>?其实很多人都理解错了

    GraniStudio:IO初始化以及IO资源配置例程

    1.文件运行 导入工程 双击运行桌面GraniStudio.exe。 通过引导界面导入IO初始化以及IO资源配置例程,点击导入按钮。 打开IO初始化以及IO资源配置例程所在路径,选中
    的头像 发表于 08-22 17:34 749次阅读
    GraniStudio:<b class='flag-5'>IO</b>初始化以及<b class='flag-5'>IO</b>资源配置例程

    GraniStudio:IO写入例程

    1.文件运行 导入工程 双击运行桌面GraniStudio.exe。 通过引导界面导入IO写入例程,点击导入按钮。 打开IO写入例程所在路径,选中IO写入.gsp文件,点击打开,完成导入。 2.功能
    的头像 发表于 08-22 16:47 616次阅读
    GraniStudio:<b class='flag-5'>IO</b>写入例程

    干货分享 | TSMaster IO功能使用指南—基于同星带IO设备的配置与操作步骤

    IO模块是一用于连接计算机系统或控制系统与外部设备之间的接口模块。数字IO模块用于处理二进制信号的输入和输出,它们可以接收和发送数字信号,通常用于控制逻辑开关、触发器和其他数字设备。模拟IO
    的头像 发表于 08-09 20:04 721次阅读
    干货分享 | TSMaster <b class='flag-5'>IO</b>功能使用指南—基于同星带<b class='flag-5'>IO</b>设备的配置与操作步骤

    Analog Devices / Maxim Integrated MAXREFDES177 IO-Link通用模拟IO特性/框图

    Analog Devices MAXREFDES177 IO-Link通用模拟IO是一款完备的IO-Link®通用模拟输入-输出 (IO) 参考设计,采用内置集成保护功能的MAX225
    的头像 发表于 06-30 09:30 557次阅读
    Analog Devices / Maxim Integrated MAXREFDES177 <b class='flag-5'>IO</b>-Link通用模拟<b class='flag-5'>IO</b>特性/框图

    边缘计算中的机器学习:基于 Linux 系统的实时推理模型部署与工业集成!

    学习如何训练模型、导出模型,并在基于Linux的系统上运行实时推理,并通过MQTT发布结果。这是一个简单但完整的流程——从工作站上的建模到在边缘设备上运行工业风格
    的头像 发表于 06-11 17:22 788次阅读
    边缘计算中的机器学习:基于 <b class='flag-5'>Linux</b> 系统的实时推理<b class='flag-5'>模型</b>部署与工业集成!

    FA模型卡片和Stage模型卡片切换

    ,Stage卡片配置在module.json5和form_config.json中(如下图1和图2)。 卡片业务逻辑:FA模型和Stage模型在卡片入口文件以及生命周期存在细微的差异(如下图3和图4
    发表于 06-06 08:10

    FA模型访问Stage模型DataShareExtensionAbility说明

    FA模型访问Stage模型DataShareExtensionAbility 概述 无论FA模型还是Stage模型,数据读写功能都包含客户端和服务端两部分。 FA
    发表于 06-04 07:53

    KaihongOS操作系统FA模型与Stage模型介绍

    FA模型与Stage模型介绍 KaihongOS操作系统中,FA模型(Feature Ability)和Stage模型是两不同的应用
    发表于 04-24 07:27

    请问如何在imx8mplus上部署和运行YOLOv5训练的模型

    我正在从事 imx8mplus yocto 项目。我已经在自定义数据集上的 YOLOv5 上训练了对象检测模型。它在 ubuntu 电脑上运行良好。现在我想在我的 imx8mplus 板上运行该模型
    发表于 03-25 07:23

    OpenAI即将推出GPT-5模型

    OpenAI首席执行官奥尔特曼近日宣布了一项重要消息:OpenAI将在今年未来几个月内推出全新的GPT-5模型。这一消息引起了业界的广泛关注和期待。 据了解,GPT-5模型将整合Ope
    的头像 发表于 02-13 11:21 916次阅读

    请问有没有不在linux上对.pt模型向.kmodel转换的教程呢?

    1、请问有没有不在linux上对.pt模型向.kmodel转换的教程呢? 我看网上有个nncase studio的教程(AI模型GUI编译工具 nncase studio食用指南 - Homura
    发表于 02-08 08:56

    【ELF 2学习板试用】ELF2开发板(飞凌嵌入式)部署yolov5s的自定义模型

    ELF2开发板(飞凌嵌入式)部署yolov5s的自定义模型` 本人将零基础教学自己训练的yolov5s模型部署于飞凌的elf2开发板,利用RKNN-Toolkit2对
    发表于 02-04 18:15

    Profinet IO通信故障原因及解决办法

    Profinet IO(Industrial Ethernet for Automation)作为一高性能的工业以太网通信协议,广泛应用于工业自动化领域。然而,在实际应用中,Profinet IO
    的头像 发表于 02-03 14:50 3132次阅读