我们拿一下常见的典型问题,作为今天的答疑内容,
首先第一个
阻塞/非阻塞IO 同步/异步IO的区别和联系
我们简单说一下不同的区别
1.首先是阻塞和非阻塞IO 根据应用程序是否阻塞自身运行分为了阻塞和非阻塞IO
阻塞IO,就是应用程序执行IO操作后,没有响应,就会阻塞当前线程
非阻塞则不会阻塞当前线程,继续执行其他任务
然后是异步和同步IO,根据IO响应的通知方式不同,分为了同步IO和异步IO
同步IO就是收到IO请求之后,系统不会响应程序,而是等处理完成,告诉应用程序IO结果
异步则是收到IO请求之后,先告诉应用程序IO请求收到了,然后进行异步处理,处理完成,利用事件通知的方式,告诉应用程序结果
阻塞和非阻塞 异步和同步,就是不同角度的IO划分方式
常见的使用
系统调用read就是同步读,
aio_read是异步读,AIO读请求获得之后就不等处理直接返回了,具体的read结果,通过回调异步通知应用程序
网络套接字中,send()直接向套接字发送数据,套接字没有设置O_NONBLOCK标识,就会一直阻塞
如果是epoll,则是非阻塞的方式使用
2.对文件系统的缓存解释
fInd / -name filename
这个命令,会不会导致系统缓存升高,如果升高了,会导致那种类型的缓存升高呢?
dentry这个数据结构,是构建文件名 文件之间的目录关系的,一个基于内存的数据结构,需要动态构建,所以Linux会动态构建不在缓存中的目录项,导致dentry缓存升高
实际上,Buffer的使用也会增加,vmstat观察一下,发现Buffer和Cache都会增长
因为构建目录项缓存所需的元数据,都需要从文件系统中读取
3.磁盘IO延迟
iostat中,IO发现了性能瓶颈,pidstat找到了大量磁盘IO进程,然后使用strace跟踪这个进程,却找不到任何的write系统调用
这是因为 strace中没有加上-f命令
因为写文件是子线程执行的,可以直接strace跟踪子进程看到
strace -fp pid 跟踪子进程
4.MySQL案例分析中的DataService
就是DataService应用停止后,MySQL的磁盘IO瓶颈消失了,为啥呢?
这是因为DataService会修改/proc/sys/vm/drop_caches,
使得数据库表,无法使用MyISAM引擎,MyISAMd的一个特点,就从内存中缓存索引,并不缓存数据,无法使用索引的时候,就需要从数据库中读入内存,进行处理
如果使用vmstat工具,可以观察缓存和IO的变化趋势
发现如下的结果
$ vmstat 1
procs ———–memory———- —swap– —–io—- -system– ——cpu—– r b swpd free buff cache si so bi bo in cs us sy id wa st # 备注: DataService正在运行 0 1 0 7293416 132 366704 0 0 32516 12 36 546 1 3 49 48 0 0 1 0 7260772 132 399256 0 0 32640 0 37 463 1 1 49 48 0 0 1 0 7228088 132 432088 0 0 32640 0 30 477 0 1 49 49 0 0 0 0 7306560 132 353084 0 0 20572 4 90 574 1 4 69 27 0 0 2 0 7282300 132 368536 0 0 15468 0 32 304 0 0 79 20 0 # 备注:DataService从这里开始停止 0 0 0 7241852 1360 424164 0 0 864 320 133 1266 1 1 94 5 0 0 1 0 7228956 1368 437400 0 0 13328 0 45 366 0 0 83 17 0 0 1 0 7196320 1368 470148 0 0 32640 0 33 413 1 1 50 49 0 … 0 0 0 6747540 1368 918576 0 0 29056 0 42 568 0 0 56 44 0 0 0 0 6747540 1368 918576 0 0 0 0 40 141 1 0 100 0 0 |
DataService停止之前,cache会连续增长三次再降回去,因为DataService每隔三秒清理一次页缓存,DataService停止之后,cache会不停的增长,直到增长到一定额度
这也是因为MyISAM引擎本身不缓存数据,而是依赖系统缓存来加速磁盘IO访问,导致会被其他的应用程序影响
InnoDB则同时缓存了索引和数据,保证了内部的可靠性