通过日常使用电脑,我们大概都知道一个机器大概的结构由CPU、内存、硬盘以及外设构成,那么Linux服务器也一样,从上一章内容知道,我们平常关注的系统性能差不多就是这些地方,那么,我们的进程是如何在Linux上运行的呢?一、进程运行过程首先,我们的数据是存放于磁盘/NAS等存储目录当中,当需要使用这些数据的时候,则要将数据从磁盘中读取出来,经过内存再到三级缓存,然后进入到CPU中。如下图,数据从底部的存储设备一步一步的被送进入到CPU中。其用于传输数据的方式:远程存储到本地二级存储走的是网络通信的方式,而本地存储的数据进入到内存、CPU走的是BUS总线的方式。
进程启动以后,其数据被从磁盘中读取到内存里缓存,当CPU使用到它的时候,再被通过三级高速缓存送入到CPU中执行。那么当这个进程被送入到CPU中运行,是不是就可以一个人独占CPU资源,直到跑完为止呢?不是的,现代系统设计出了上下文切换的模式,每个进程运行的时候都会分配到了一个时间片,当这个时间片用完,那么当前正在运行的进程就会保留当前的状态进入到缓存当中,当再次轮到该进程使用CPU的时候,才会从缓存当中被读取出来。通过这样反复的切换,直到进程运行结束。但是我们在使用进程时,为什么没有进程切换的感觉呢?那是因为CPU的时间片以非常小的时间单位工作着,人们根本感受不到他的切换频率。在Linux系统中存在着两个空间,一个是用户空间,另外一个就是内核空间。用户空间指的是用户可以操作和访问的空间,这个空间通常存放我们用户自己写的数据等,比如磁盘NAS就是属于用户空间。内核空间就是系统内核来操作的一块空间,这块空间里面存放系统内核的函数、接口等,用户是不能直接操作的。当程序在用户空间下运行,我们把此时运行的程序的这种状态称为用户态,而当进程执行在内核空间时,这种状态称为内核态。要想让程序从用户态切换到内核态,有3种方法:1.系统调用 (软中断)2.异常(硬中断) 3.外围设备的中断(硬中断)。二、进程异常会遇到什么?进程在运行过程中不是一开始就知道使用多少内存的,在持续的运行过程中,会不断的向系统申请内存。当有应用需要读写磁盘数据时,由系统把相关数据从磁盘读取到内存,如果物理内存不够,则把内存中的部分数据导入到磁盘,从而把磁盘的部分空间当做虚拟内存使用,这部分被称为swap。如果给所有应用分配足够内存后,物理内存还有剩余,Linux会尽量再利用这些空闲内存,以提高整体I/O效率,方法是把这部分剩余内存再划分为cache和buffer加以利用。如果某个时刻,系统需要更多的内存,则会把cache部分擦除,并把buffer中的内容写入到磁盘中,然后把这两部分的空间释放给系统使用,但是再次读取cache的内容时,就需要重新从磁盘读取数据。下图是系统中存在的缓存,当系统需要内存时,就会被释放空间,然后充当内存使用。
1) Page cache主要用来作为文件系统上的文件数据缓存来用,尤其是对当进程对文件有read/write操作的时候。2) Buffer cache主要是用来在系统对块设备进行读写的时候,对块设备进行数据缓存来使用。3) directory cacha的作用是作为目录缓存,避免经常访问目录慢。4) iNode cache则能够加速访问文件速度。同一系统内的文件具有唯一识别码,这个就是iNode号。查找文件的时候会先查询该文件的iNode号,再根据iNode号定位到文件位置。一般可以理解为buffer是为了作为数据写入磁盘时的一个缓冲地带。把分散的写操作集中进行,减少磁盘碎片和硬盘的反复寻道,从而提高系统性能。而cache经常被用于磁盘的I/O请求上,如果多个进程都有访问某个文件,于是该文件便被作为cache以方便下次被访问,这样可以提高系统性能。
三、当运行一个进程时系统内存不够会怎么样?
在工作中会遇到这样的场景:假设我的服务器就只有32G内存,当前以及使用了28G,而现在需要再运行一个需要10G内存的进程,那么会发生什么呢?
如果这个进程没有做什么优先级设定,那么这个进程会触发OOM,然后被系统kill掉。
什么是OOM?
OOM的全称是Out of memory Killer,叫内存终结者。在内存过低的情况下,OS(系统)会杀掉你的进程。当探测到内存使用不足的时候,OOM会被激活,然后挑选一个进程去终结掉。选择的目标进程使用的是一套算法,后面会说。
进程在运行过程中是怎么使用内存的呢?Linux允许程序申请比系统可用内存更多的内存,这个机制叫做Overcommit。这样做是处于优化系统考虑,因为不是所有的程序申请了内存就立刻使用的,当开始使用的时候,可能系统已经回收了一些资源,但是当使用overcommit给的内存时,系统还没有资源的话,这个时候就会触发OOM,然后干掉进程。
有的时候在系统内存不是很充足的情况下需要运行一个重要的程序,那么该如何避免此程序被OOM干掉呢?
调整进程的oom_adj值:Linux下每个进程都有个OOM权重,在/proc/$pid/oom_adj里面,取值-17~+15,取值越高,越容易被干掉。
OOM Killer最终是通过/proc/$pid/oom_score这个值来决定哪个进程被干掉。这个值是系统综合进程的内存消耗量、CPU时间、存活时间和oom_adj计算出来的。消耗内存越多分越高,存活时间越长分越低。总之。总的策略就是:损失最少的工作,释放最大的内存同时不伤及无辜的用来很大内存的进程,并且杀掉的进程数尽量少。另外,Linux在计算进程的内存消耗的时候,会将子进程所耗内存的一半同时计算到父进程中,这样子进程较多的进程就越容易被杀掉。
在Linux中如何查看是否有进程被OOM干掉了呢?
运行dmesg即可查询到,或者到/var/log/messages中查看。从网上找了个OOM的图:
-
cpu
+关注
关注
68文章
10840浏览量
211395 -
Linux
+关注
关注
87文章
11254浏览量
209106 -
服务器
+关注
关注
12文章
9063浏览量
85274
发布评论请先 登录
相关推荐
评论