首页
学习
活动
专区
工具
TVP
发布
精选内容/技术社群/优惠产品,尽在小程序
立即前往

Linux内核如何知道将输入事件写入哪个文件描述符?

Linux内核通过文件描述符(File Descriptor)来标识和管理打开的文件或者其他I/O资源。文件描述符是一个非负整数,它在内核中被用作索引,指向进程打开文件表中的相应文件表项。

当一个输入事件发生时,Linux内核会通过输入设备驱动程序将事件读取到内核空间。然后,内核会根据当前的进程上下文,即当前运行的进程,来确定将输入事件写入哪个文件描述符。

在Linux中,每个进程都有一个进程表项(Process Control Block),其中包含了进程的各种信息,包括打开文件表。打开文件表是一个指向文件表项的指针数组,每个文件表项包含了文件的状态信息和指向文件操作函数的指针。

当一个进程打开一个文件时,内核会在打开文件表中创建一个文件表项,并返回一个文件描述符给进程。文件描述符是一个索引,它指向打开文件表中的相应文件表项。

因此,当一个输入事件发生时,内核会根据当前进程的上下文,查找该进程的打开文件表,找到相应的文件表项,然后将输入事件写入该文件描述符所指向的文件表项。

需要注意的是,具体的实现细节可能会因不同的Linux发行版和内核版本而有所差异。此外,Linux内核还提供了一些系统调用(如selectpollepoll等)来帮助进程管理和处理输入事件。这些系统调用可以用于监视多个文件描述符的状态,并在有事件发生时通知进程进行相应的处理。

推荐的腾讯云相关产品:腾讯云服务器(CVM)和腾讯云容器服务(TKE)。

  • 腾讯云服务器(CVM):腾讯云提供的弹性云服务器,可根据业务需求灵活调整配置和规模。详情请参考:腾讯云服务器产品介绍
  • 腾讯云容器服务(TKE):腾讯云提供的容器集群管理服务,可帮助用户快速构建、部署和管理容器化应用。详情请参考:腾讯云容器服务产品介绍
页面内容是否对你有帮助?
有帮助
没帮助

相关·内容

计网 - Socket 编程:epoll 为什么用红黑树?

当一个客户端连接到服务端的时候,操作系统就会创建一个客户端 Socket 的文件。然后操作系统这个文件文件描述符写入服务端程序创建的服务端 Socket 文件中。...端口监听不能冲突,不然客户端连接进来创建客户端 Socket 文件文件描述符就不知道写入哪个服务端 Socket 文件了。...当一个 Socket 文件发生变化的时候,中间观察者需要立刻知道,究竟是哪个线程需要这个信息,而不是所有的线程都遍历一遍 ---- 为什么用红黑树? 关于为什么要红黑树, 再仔细解释一下。...在 select 模型下,操作系统不知道哪个线程应该响应哪个事件,而是由线程自己去操作系统看有没有发生网络 I/O 事件,然后再遍历自己管理的所有 Socket,看看这些 Socket 有没有发生变化。...epoll 模型在操作系统内核中提供了一个中间数据结构,这个中间数据结构会提供事件监听注册,以及快速判断消息关联到哪个线程的能力(红黑树实现)。

3.5K30

深入学习IO多路复用 selectpollepoll 实现原理

吃水不忘挖井人,最近两周花了些时间学习了张彦飞大佬的文章 图解 | 深入揭秘 epoll 是如何实现 IO 多路复用的 和其他文章 ,及出版的书籍《深入理解 Linux 网络》,对阻塞 IO、多路复用、...,不知道哪些连接已就绪即收到了数据,需要遍历传递进来的所有 fd_set 的每一位,不管它们是否就绪;(epoll 优化为异步事件通知) c)select 只返回就绪文件的个数,具体哪个文件可读还需要遍历...这种回调机制能够定向准确的通知程序要处理的事件,而不需要每次都循环遍历检查数据是否到达以及数据该由哪个进程处理,日常开发中可以学习借鉴下这种思想。 1....非阻塞 IO 模型如下图所示: 图1.3 非阻塞IO模型 从上图中,我们知道,非阻塞 IO,是等待数据从网卡到达 socket 内核空间这一部分变成了非阻塞的,用户进程调用 recvfrom() 会重复发送请求检查数据是否到达内核空间...2)进程被唤醒后,不知道哪些连接已就绪即收到了数据,需要遍历传递进来的所有 fd_set 的每一位,不管它们是否就绪;(epoll 优化为异步事件通知) 3)select 只返回就绪文件的个数,具体哪个文件可读还需要遍历

3.8K77

深入学习IO多路复用selectpollepoll实现原理

b)进程被唤醒后,不知道哪些连接已就绪即收到了数据,需要遍历传递进来的所有 fd_set 的每一位,不管它们是否就绪;(epoll 优化为异步事件通知) c)select 只返回就绪文件的个数...这种回调机制能够定向准确的通知程序要处理的事件,而不需要每次都循环遍历检查数据是否到达以及数据该由哪个进程处理,日常开发中可以学习借鉴下这种思想。 1....非阻塞 IO 模型如下图所示: 图片 从上图中,我们知道,非阻塞 IO,是等待数据从网卡到达 socket 内核空间这一部分变成了非阻塞的,用户进程调用 recvfrom() 会重复发送请求检查数据是否到达内核空间...文件描述符 fd 文件描述符(file descriptor)是一个非负整数,从 0 开始。进程使用文件描述符来标识一个打开的文件Linux 中一切皆文件。...只返回就绪文件的个数,具体哪个文件可读还需要遍历; (epoll 优化为只返回就绪的文件描述符,无需做无效的遍历) 2.

1.6K52

select、poll、epoll

select并不知道是属于哪个流的,需要遍历传递进来的所有fd,那么每次轮询遍历的事件复杂度是O(n),这个开销在fd很多时也很大 (3)select最大可支持的描述符个数为1024个 (4)每次调用select...前都要重新设置文件描述符集合和时间,因为内核会修改传入的参数数组 二、poll poll技术与select技术实现逻辑基本一致,重要区别在于其使用链表的方式存储描述符fd,没有最大连接数的限制,但是对于...epoll通过在Linux内核中申请一个简易的文件系统来管理多个文件描述符。...当某一进程调用epoll_create方法时,Linux内核会创建一个eventpoll结构体,红黑树方便快速找到与文件描述符相关的epitem结构。...,而epoll只要一次拷贝,epoll在内核中通过虚拟内存方式内核空间与用户空间的一块地址同时映射到相同的物理内存地址中,这块内存对用户空间以及内核空间均为可见,因此可以减少用户空间与内核空间之间的数据拷贝

1.1K30

彻底搞懂epoll高效运行的原理

I/O 输入输出(input/output)的对象可以是文件(file), 网络(socket),进程之间的管道(pipe)。在linux系统中,都用文件描述符(fd)来表示。...事件 可读事件,当文件描述符关联的内核读缓冲区可读,则触发可读事件。(可读:内核缓冲区非空,有数据可以读取) 可写事件,当文件描述符关联的内核写缓冲区可写,则触发可写事件。...(可写:内核缓冲区不满,有空闲空间可以写入) 通知机制 通知机制,就是当事件发生的时候,则主动通知。通知机制的反面,就是轮询机制。...用户态文件描述符传入内核的方式 select:创建3个文件描述符集并拷贝到内核中,分别监听读、写、异常动作。这里受到单个进程可以打开的fd数量限制,默认是1024。...在执行epoll_ctl的add操作时,不仅文件描述符放到红黑树上,而且也注册了回调函数,内核在检测到某文件描述符可读/可写时会调用回调函数,该回调函数文件描述符放在就绪链表中。 3.

1.8K32

epoll、poll、select的原理和区别

epoll是一种I/O事件通知机制,是linux 内核实现IO多路复用的一个实现。...输入输出(input/output)的对象可以是文件(file), 网络(socket),进程之间的管道(pipe)。在linux系统中,都用文件描述符(fd)来表示。 什么是事件?...内核缓冲区非空,有数据可以读取);可写事件,当文件描述符关联的内核写缓冲区可写,则触发可写事件(可写:内核缓冲区不满,有空闲空间可以写入)。...在执行epoll_ctl的add操作时,不仅文件描述符放到红黑树上,而且也注册了回调函数,内核在检测到某文件描述符可读/可写时会调用回调函数,该回调函数文件描述符放在就绪链表中。 3....找到就绪的文件描述符并传递给用户态的方式 select:将之前传入的fd_set拷贝传出到用户态并返回就绪的文件描述符总数。用户态并不知道是哪些文件描述符处于就绪态,需要遍历来判断。

1.6K21

深入分析select&poll&epoll原理

首先,我们要了解IO复用模型之前,先要了解在Linux内核中socket事件机制在内核底层是基于什么机制实现的,它是如何工作的,其次,当我们对socket事件机制有了一个基本认知之后,那么我们就需要思考到底什么是...Linux内核事件机制 在Linux内核中存在着等待队列的数据结构,该数据结构是基于双端链表实现,Linux内核通过阻塞的进程任务添加到等待队列中,而进程任务被唤醒则是在队列轮询遍历检测是否处于就绪状态...,这个时候只需要等待内核数据复制到用户空间的缓冲区中就可以了.那么对于read_process而言,要实现复用该如何设计才能达到上述的效果呢?...socket描述符可读在Linux内核称为事件,其设计实现的逻辑图如下所示: ?...这个时候网卡设备接收到网络发起的数据请求数据,内核接收到数据报,就会通过轮询唤醒的方式(内核并不知道哪个socket可读)逐个进行唤醒通知,直到当前socket描述符有可读状态的时候就退出轮询然后从等待队列移除对应的

95031

NIO,epoll,多路复用,更好地理解IO

非阻塞的( socket Linux 2.6.27内核开始支持非阻塞模式。)...是否可以O(n)的复杂度进行一个降解,这一块还是要看内核怎么做优化的,我们可以看下select这个命令,下面关于它的描述是“ 允许一个程序监听多个文件描述符,等待一个或者多个文件描述符变成了可用状态...通过下面的图就容易理解点,程序先调了一个叫select的系统调用,然后传入fds(如果有1w个文件描述符,在这一次的系统调用中将这1w个文件描述符发给内核),内核会返回若干个可用状态的文件描述符,最终读数据是基于这若干个可用状态的文件描述符访问内核去读...,减少了传递的过程,那么如何知道这些fd哪些是可读/可写的呢?...◆ epoll_wait 阻塞等待注册的事件发生,返回事件的数目,并将触发的可用事件写入epoll_events数组中。

47330

一文说清BIO、NIO、AIO不同IO模型演进之路

我们都知道无论是程序还是平台,它们的功能高度抽象之后其实可以描述为这样一个过程,即为通过外部条件以及数据的输入,经过程序或者平台的处理产生了新的输出,IO模型实际上就是描述了计算机世界中的输入和输出过程的模式...应用从流中读取数据即为read操作,当把流中的数据进行写入的时候就是write操作。但是linux系统又是如何区分不同类型的文件呢?...实际是通过文件描述符(File Descriptor)来进行区分,文件描述符其实就是个整数,这个整数实际是一个索引值,指向内核为每一个进程所维护的该进程打开文件的记录表。...在实际场景中,后端服务器接收大量的socket连接,IO多路复用是实际是使用了内核提供的实现函数,在实现函数中有一个参数是文件描述符集合,对这些文件描述符(FD)进行循环监听,当某个文件描述符(FD)就绪时...我们都知道问题的根源就是BIO模型中我们不知道数据的读取与写入的时机,才导致的阻塞等待,那么如果我们能够知道数据读写的时机,是不是就不用傻傻的等着响应,也不用再创建新的线程来处理连接了。

48430

手拿放大镜深究文件IO

同步I/O与页回写 数据只有在被写入磁盘中才算写入成功,但是进程又无法直接读写磁盘,只能借由内核提供的系统调用函数进行操作,上文所述的write就是linux内核提供给用户空间写磁盘的系统函数,那么,write...从上图中可以看到,linux系统在进程发起write系统调用时,只是数据写入内核缓冲区中的页缓存即返回,内核空间页缓存中的数据刷新到磁盘(步骤⑧ )是异步的。...因为内核并不知道某一页的数据是由哪些用户线程写入,即使知道了,也无法通知它们,因为刷盘是异步的,此时可能用户线程已经销毁。 进而,什么情况下会造成页回写失败呢?...linux引入内核缓冲区,需要写的数据更新到内核缓冲区后即返回,大大提升了write系统调用的性能。...下面代码想要达到的效果是,监听两个已打开的文件(分别是标准输入和标准错误,实际使用时,可以替换成任意已打开的文件文件描述符)读事件,当这些文件中任意一个有数据可读时,拿到这些可读的文件描述符,随后进行读取

82330

一文读懂Redis中的多路复用模型

后由于 select 的一些痛点比如它在 32 位系统下,单进程支持最多打开 1024 个文件描述符linux 对 IO 等操作都是通过对应的文件描述符实现的 socket 对应的是 socket 文件描述符...事件,会由对应的命令回复处理器来处理,就是准备好的响应数据写入 Socket,供客户端来读取。...这样,就无需遍历成千上万个消息列表了,直接可以定位哪个socket有数据。 那么,这是如何实现的呢?...用户态并不知道是哪些文件描述符处于就绪态,需要遍历来判断。 epoll:epoll_wait只用观察就绪链表中有无数据即可,最后链表的数据返回给数组并返回就绪的数量。...内核将就绪的文件描述符放在传入的数组中,所以只用遍历依次处理即可。这里返回的文件描述符是通过mmap让内核和用户空间共享同一块内存实现传递的,减少了不必要的拷贝。

76421

深入分析select&poll&epoll原理

首先,我们要了解IO复用模型之前,先要了解在Linux内核中socket事件机制在内核底层是基于什么机制实现的,它是如何工作的,其次,当我们对socket事件机制有了一个基本认知之后,那么我们就需要思考到底什么是...Linux内核事件机制 在Linux内核中存在着等待队列的数据结构,该数据结构是基于双端链表实现,Linux内核通过阻塞的进程任务添加到等待队列中,而进程任务被唤醒则是在队列轮询遍历检测是否处于就绪状态...,这个时候只需要等待内核数据复制到用户空间的缓冲区中就可以了.那么对于read_process而言,要实现复用该如何设计才能达到上述的效果呢?...socket描述符可读在Linux内核称为事件,其设计实现的逻辑图如下所示: 用户进程向内核发起select函数的调用,并携带socket描述符集合从用户空间复制到内核空间,由内核对socket集合进行可读状态的监控...这个时候网卡设备接收到网络发起的数据请求数据,内核接收到数据报,就会通过轮询唤醒的方式(内核并不知道哪个socket可读)逐个进行唤醒通知,直到当前socket描述符有可读状态的时候就退出轮询然后从等待队列移除对应的

3.1K40

Linux下的IO复用与epoll详解

linux上,2.4内核前主要是select和poll,自Linux 2.6内核正式引入epoll以来,epoll已经成为了目前实现高性能网络服务器的必备技术。...epoll_wait系统调用的参数events仅用来反馈就绪的事件 应用程序索引就绪文件描述符的时间复杂度 O(n) O(n) O(1) 最大支持文件描述符数 一般有最大值限制 65535 65535...maxevents:指定最多监听多少个事件      events:检测到事件所有就绪的事件内核事件表中复制到它的第二个参数events指向的数组中。  ...如何知道是否处理完就绪队列中的所有连接呢? accept  返回 -1 并且 errno 设置为 EAGAIN 就表示所有连接都处理完。       ...参考资料: Linux开发必备:IO多路复用剖析 Linux开发必备:1小时玩转儿文件I/O编程 linux下的IO模型

1.9K10

万字图解| 深入揭秘IO多路复用

Linux 常见网络IO事件定义 一、从一次网络调用说起 假设应用A想要请求应用B获取数据,那么他会经历以下步骤: 应用A请求报文写入自己的TCP写缓冲区 应用A的请求报文经过网线到达应用B的TCP...读缓冲区 应用B获得请求报文后,进行业务逻辑处理 应用B业务逻辑处理完成后,响应报文写入自己的TCP写缓冲区,然后经过网线达到应用A的TCP读缓冲区 现在我们注意力放到应用A上,应用A请求发送出去后...*set); // 文件描述符fd添加到set集合中 void FD_SET(int fd, fd_set *set); // set集合中, 所有文件描述符对应的标志位设置为0 void...,struct pollfd有三个成员: fd:委托内核检测的文件描述符 events:委托内核检测的fd事件输入、输出、错误),每一个事件有多个取值 revents:这是一个传出参数,数据由内核写入...epoll 文件描述符添加和检测分离,减少了文件描述符拷贝的消耗 select&poll 调用时会将全部监听的 fd 从用户态空间拷贝至内核态空间并线性扫描一遍找出就绪的 fd 再返回到用户态。

2.1K22

图文详解 epoll 原理【Redis,Netty,Nginx实现高性能IO的核心原理】epoll 详解

输入输出(input/output)的对象可以是文件(file), 网络(socket),进程之间的管道(pipe)。在linux系统中,都用文件描述符(fd)来表示。...事件 可读事件,当文件描述符关联的内核读缓冲区可读,则触发可读事件。 (可读:内核缓冲区非空,有数据可以读取) 可写事件,当文件描述符关联的内核写缓冲区可写,则触发可写事件。...用户态文件描述符传入内核的方式 select:创建3个文件描述符集并拷贝到内核中,分别监听读、写、异常动作。这里受到单个进程可以打开的fd数量限制,默认是1024。...在执行 epoll_ctl 的add操作时,不仅文件描述符放到红黑树上,而且也注册了回调函数;内核在检测到某文件描述符可读/可写时会调用回调函数,该回调函数文件描述符放在就绪链表中。 3....poll:将之前传入的 fd 数组拷贝传出用户态,并返回就绪的文件描述符总数。用户态并不知道是哪些文件描述符处于就绪态,需要遍历来判断。

9.5K94

程序员的23大IO&NIO面试问题及答案

比如文件拷贝,输入流和输出流都包括了。输入流从文件中读取数据存储到进程(process)中,输出流从进程中读取数据然后写入到目标文件。 2.java中有几种类型的流? 按照单位大小:字符流、字节流。...按照流的方向:输出流、输入流。 3.字节流和字符流哪个好?怎么选择?...,因为字符流具备缓冲区,提高了性能 4.读取数据量大的文件时,速度会很慢,如何选择流?...,把所有IO流都轮询一遍,于是没有IO事件我们的程序就阻塞在select方法处,即便这样依然存在问题,我们从select出只是知道有IO事件发生,却不知道是哪几个流,还是只能轮询所有流,epoll这样的代理就可以把哪个流发生怎样的...,而这些文件描述符(套接字描述符)其中任意一个进入就绪状态,select函数就可以返回。

33720

一口气说出 5 种 IO 模型,懵逼了

select select系统调用允许程序同时在多个底层文件描述符上,等待输入的到达或输出的完成。以数组形式存储文件描述符,64位机器默认2048个。...当有数据准备好时,无法感知具体是哪个流OK了,所以需要一个一个的遍历,函数的时间复杂度为O(n)。 poll 以链表形式存储文件描述符,没有长度限制。...epoll 是基于事件驱动的,如果某个流准备好了,会以事件通知,知道具体是哪个流,因此不需要遍历,函数的时间复杂度为O(1)。.../数据准备好后,数据拷贝到内核空间的缓冲区中,再从内核空间拷贝到用户空间的缓冲区。...select函数会不断地轮询自己所负责的文件描述符/套接字的到达状态,当某个套接字就绪时,就对这个套接字进行处理。select负责轮询等待,recvfrom负责拷贝。

70730

select,poll,epoll区别

第一个参数n,等于所有set中最大的那个文件描述符的值加1。因此,select()的调用者负责检查哪个文件描述符拥有最大值,并且把这个值加1再传递给第一个参数。...如果timeout中的两个值都设置为0,则调用select()立即返回,报告调用时所有未决的事件,但不等待任何随后的事件文件描述符set不会直接操作,一般使用几个助手宏来管理。...每个结构体的events域是监视该文件描述符事件掩码,由用户来设置这个域。revents域是文件描述符的操作结果事件掩码。内核在调用返回时设置这个域。...如果POLLOUT被设置,则文件描述符可以写入而不导致阻塞。这些标志并不是互斥的:它们可能被同时设置,表示这个文件描述符的读取和写入操作都会正常返回而不阻塞。...无论是select,poll还是epoll都需要内核把FD消息通知给用户空间,如何避免不必要的内存拷贝就很重要,在这点上,epoll是通过内核于用户空间mmap同一块内存实现的。

1.3K21

内核接收数据到EPOLL原理

四、工作队列和等待队列 工作队列和等待队列.png 工作队列:为了方便时间片的调度,所有“可运行状态”状态的进程组成的队列; fd文件列表:内核打开的文件句柄,Linux一切皆文件,用户线程执行创建...但是此时线程A 并不知道哪个socket有数据,于是还要遍历readSet使用 FD_ISSET 来逐个查看是哪个socket的有数据可读。...poll 主要解决 select 的前两个问题:通过改变跟内核交互的数据结构突破了文件描述符的限制,同时使用不同字段分别标注关注事件和发生事件,来避免重复初始化。...:epoll_create 创建的 epoll 实例句柄 # op:增加还是删除一个监控事件 # fd:注册的事件文件描述符 # event:注册的事件类型,并且可以在这个结构体里设置用户需要的数据...:当某个socket有事件发生时,中断处理程序就会把该socket加入到就绪队列,同时唤醒eventpoll 阻塞队列中的线程,此时线程只需要遍历就绪队列就可以知道哪个socket有事件发生,例如:图中

1K84

EPOLL原理详解

四、工作队列和等待队列 工作队列和等待队列.png 工作队列:为了方便时间片的调度,所有“可运行状态”状态的进程组成的队列; fd文件列表:内核打开的文件句柄,Linux一切皆文件,用户线程执行创建...但是此时线程A 并不知道哪个socket有数据,于是还要遍历readSet使用 FD_ISSET 来逐个查看是哪个socket的有数据可读。...poll 主要解决 select 的前两个问题:通过改变跟内核交互的数据结构突破了文件描述符的限制,同时使用不同字段分别标注关注事件和发生事件,来避免重复初始化。...:epoll_create 创建的 epoll 实例句柄 # op:增加还是删除一个监控事件 # fd:注册的事件文件描述符 # event:注册的事件类型,并且可以在这个结构体里设置用户需要的数据...:当某个socket有事件发生时,中断处理程序就会把该socket加入到就绪队列,同时唤醒eventpoll 阻塞队列中的线程,此时线程只需要遍历就绪队列就可以知道哪个socket有事件发生,例如:图中

1.6K00
领券