ICode9

精准搜索请尝试: 精确搜索
首页 > 其他分享> 文章详细

浅谈NIO和Epoll实现原理

2021-11-24 17:33:14  阅读:133  来源: 互联网

标签:NIO Epoll 21 fd 内核 线程 Nov root 浅谈


1 前置知识

1.1 socket是什么?

就是传输控制层tcp连接通信。

1.2 fd是什么?

fd既file descriptor-文件描述符。Java中用对象代表输入输出流等...在Linux系统中不是面向对象的,是一切皆文件的,拿文件来代表输入输出流。其实是一个数值,例如1,2,3,4...0是标准输入,1是标准输出,2是错误输出...

任何进程在操作系统中都有自己IO对应的文件描述符,参考如下:
[root@iZj6c1dib207c054itjn30Z ~]# ps -ef | grep redis
root     20688     1  0 Nov23 ?        00:01:01 /opt/redis/bin/redis-server 127.0.0.1:6379
root     20786     1  0 Nov23 ?        00:01:00 /opt/redis/bin/redis-server 127.0.0.1:6380
root     30741 30719  0 12:26 pts/1    00:00:00 grep --color=auto redis
[root@iZj6c1dib207c054itjn30Z ~]# cd /proc/20688/fd
[root@iZj6c1dib207c054itjn30Z fd]# ll
total 0
lrwx------ 1 root root 64 Nov 23 21:50 0 -> /dev/null
lrwx------ 1 root root 64 Nov 23 21:50 1 -> /dev/null
lrwx------ 1 root root 64 Nov 23 21:50 2 -> /dev/null
lr-x------ 1 root root 64 Nov 23 21:50 3 -> pipe:[27847377]
l-wx------ 1 root root 64 Nov 23 21:50 4 -> pipe:[27847377]
lrwx------ 1 root root 64 Nov 23 21:50 5 -> anon_inode:[eventpoll]
lrwx------ 1 root root 64 Nov 23 21:50 6 -> socket:[27847384]

2 从BIO到epoll

2.1 BIO

计算机有内核,客户端和内核连接产生fd,计算机的进程或线程会读取相应的fd。 因为socket在这个时期是blocking的,线程读取socket产生的文件描述符时,如果数据包没到,读取命令不能返回,会被阻塞。导致会有更多的线程被抛出,单位CPU在某一时间片只能处理一个线程,出现数据包到了的线程等着数据包没到的线程的情况,造成CPU资源浪费,CPU切换线程成本巨大。 例如早期Tomcat7.0版默认就是BIO。  

 

2.2 早期NIO

socket对应的fd是非阻塞的 单位CPU只用一个线程,就一颗CPU只跑一个线程,没有CPU切换损耗,在用户空间轮询遍历所有的文件描述符。从遍历到取数据都是自己完成,所以是同步非阻塞IO。 问题是如果有1000个fd,代表用户进程轮询调用1000次kernel, 用户空间查询一次文件描述符就得调用一次系统调用,让后内核态用户态来回切换成本很大。

 

2.3 多路复用NIO

内核向前发展,轮询放到内核里,内核增加一个系统调用select函数,统一把一千个fd传给select函数,内核操作select函数,fd准备好后返回给线程,拿着返回的文件描述符找出ready的再去调read。如果1000个fd只有1个有数据,以前要调1000次,现在只调1次,相对前面在系统调用上更加精准。还是同步非阻塞的,只是减少了用户态和内核态的切换。 Linux只能实现NIO,不能实现AIO 问题:用户态和内核态沟通的fd相关数据要来回拷贝  

 

2.3 epoll

内核通过mmap实现共享空间,用户态和内核态有一个空间是共享的,文件描述符fd存在共享空间实现用户态和内核态共享。epoll里面有三个调用,用户空间先epoll_create准备一个共享空间mmap,里面维护一个红黑树,内核态将连接注册进红黑树,epoll_ctl写入。当有数据准备好了,调用epoll_wait中断阻塞,取链表fd,再单独调用read mmap应用:kafka实现数据通过socket存到服务器文件上的过程也是mmap epoll应用:redis和nginx的worker进程等等

 

标签:NIO,Epoll,21,fd,内核,线程,Nov,root,浅谈
来源: https://www.cnblogs.com/dpf-hzm/p/15599143.html

本站声明: 1. iCode9 技术分享网(下文简称本站)提供的所有内容,仅供技术学习、探讨和分享;
2. 关于本站的所有留言、评论、转载及引用,纯属内容发起人的个人观点,与本站观点和立场无关;
3. 关于本站的所有言论和文字,纯属内容发起人的个人观点,与本站观点和立场无关;
4. 本站文章均是网友提供,不完全保证技术分享内容的完整性、准确性、时效性、风险性和版权归属;如您发现该文章侵犯了您的权益,可联系我们第一时间进行删除;
5. 本站为非盈利性的个人网站,所有内容不会用来进行牟利,也不会利用任何形式的广告来间接获益,纯粹是为了广大技术爱好者提供技术内容和技术思想的分享性交流网站。

专注分享技术,共同学习,共同进步。侵权联系[81616952@qq.com]

Copyright (C)ICode9.com, All Rights Reserved.

ICode9版权所有