每天3分钟操作系统修炼秘籍(12):OOM和swap分区

点我查看秘籍连载

OOM和swap分区

进程的虚拟内存空间是映射到整个物理内存空间的,所以在进程自身看来它拥有了整个物理内存,它也能使用整个物理内存,只需在使用的时候请求操作系统帮忙分配更多空间即可。

但是,操作系统上并非只运行了一个进程,如果一个进程无休止的申请物理内存空间,最终会导致物理内存耗尽或即将耗尽,使得操作系统无法创建新进程,因为创建新进程需要为它分配虚拟内存。

所以,操作系统必须得监视物理内存的使用情况,在出现物理内存耗尽或即将耗尽的时候,如果进程继续请求分配内存,将报错out-of-memory(OOM)表示内存不足,并且在出现OOM的时候,操作系统将触发OOM Killer程序从进程列表中筛选出一个内存密集型进程杀掉,从而释放大片内存。但显然,这是不怎么友好的方式,不少服务器都专门或主要运行一个服务,如果这个服务进程正好申请了大量内存,它很可能会被OOM Killer杀掉,从而导致服务停止。

其实,早期内存一般都比较小,很容易就出现内存不足的问题,所以很早就提出了一个交换分区(swap partition)的概念。

swap分区是将磁盘当作内存使用,使得虚拟地址空间的范围大小可以超出物理内存的实际大小,在物理内存空间不足时,可以将物理内存中的一些不重要数据拷贝到磁盘的swap分区中,从而让出内存空间,并且在需要那些已被拷出数据时再从swap分区中拷回到内存,从而不再那么容易发生OOM错误。

但是swap分区毕竟是在磁盘上,并且要在内存和磁盘之间传递数据,所以要访问swap分区上的数据时速度会非常慢。在目前大内存都已足够廉价的情况下,已经没有多少必要使用swap分区。

虽然,现在swap分区对进程来说很少派上用场,但涉及到的一些技术和概念有必要简单介绍下。

使用swap分区第二个要解决的问题是,如何让虚拟地址空间的页映射到磁盘swap分区的页上。也就是,如何将虚拟页翻译成swap页,并且在访问时怎么知道这不是内存的物理页。

因为在物理内存的基础上引入了swap分区,所以每个虚拟页中都有一个存在位来表示该页是否存在于内存中,如果该位的值为1,表示驻留在内存中,如果为0则表示在swap分区而非内存。其中,所有驻留在内存中的页也称为驻留集(Resident Set)。

当访问一个虚拟页的时候,如果发现不在内存中,这时候会产生缺页异常(page fault),也称为页未命中(page miss),于是陷入操作系统,启动页错误处理程序,从swap分区中找到对应的页(显然,这里需要将虚拟内存页翻译成swap分区页的地址)并拷贝到内存中。从swap分区拷入页的过程称为换入页(page in)。

这里产生了一个新问题,既然已经使用了swap分区,说明此时物理内存已经处于紧张状态,从swap中page in的页如何放进内存中?其实,这里也需要先进行page out,将该进程的一页或多页page out以便腾出内存。那么哪些运气不好的页会被page out呢?这里又出现了策略算法,称为页替换策略算法,用来决定哪些页应该被page out,比如使用FIFO算法换出那些先进入的页,使用随机算法随机选择换出的页,使用LRU算法选择最近最不常用的页等等。

其实,除了page out换出页腾出少量内存空间外,操作系统还设置了两个关于空闲页数量(显然,这是物理页)的水位线:高水位线(High Watermark,HW)和低水位线(Low Watermark,LW)。当操作系统发现空闲页的数量少于低水位线的值时,就会自动启动一个称为swap daemon(也称为page daemon)的后台线程kswapd,该线程会扫描所有进程并从中选出一些候选进程,然后将这些进程的所有页都拷贝到swap分区,直到空闲物理内存页的数量达到高水位线的值。

提示:高水位线和低水位线

在计算机领域中,常会使用高水位线和低水位线来监视进程的一些可用性资源。当这类可用性资源的数量高于或临近高水位线的值时,表明资源充足。当可用性资源的数量已经低于低水位线,说明资源紧张,应当采取一些措施恢复一些资源。

其中,换出进程所有页到swap分区的过程称为swap out,而从swap分区拷入进程所有页的过程(比如再次调度到该进程)称为swap in。将这两个概念与page out和page in区分以下:

  • page in和page out是拷入或拷出进程的一页或某些页
  • swap in和swap out是拷入或拷出进程的所有页

关于swap分区,能不用的话最好还是不用,因为当真正用到swap分区的时候,内存已经进入了紧张状态,之后的绝大多数进程基本上都会涉及到swap分区,不断地出现page fault而进行换页,这会导致进程抖动(thrashing),使得整体效率低下,而且这个状态是持续的,直到释放足够的内存空间。这时候还不如采取其它办法释放内存空间,例如杀掉某些无关进程、重启内存密集型服务、重启机器等。

原文地址:https://www.cnblogs.com/f-ck-need-u/p/11793972.html

时间: 2024-09-30 02:01:20

每天3分钟操作系统修炼秘籍(12):OOM和swap分区的相关文章

每天3分钟操作系统修炼秘籍(2):并行的假象和分时系统

点我查看秘籍连载 假象:"并行"运行多个进程 现代操作系统都支持多任务同时执行.在这里,操作系统对我们用户"营造了一种假象",让CPU看上去是用不完的,能够不断地添加新的程序使它们同时运行. 但每核CPU在某一时刻都只能执行一个进程.使用操作系统的人是不会去关注CPU是单核还是多核的,每个人都希望操作系统能同时运行多个程序,比如可以同时看网页.发邮件.聊QQ.听音乐等. 所以操作系统提供的多程序同时运行是"伪并行".要想实现真正的并行运行多个进程

每天3分钟操作系统修炼秘籍(7):虚拟内存简介

点我查看秘籍连载 资源隔离:虚拟内存 前面描述的所有操作系统基础知识都是进程和CPU资源相关的内容,另一个操作系统中和进程相关的比较重要的话题是内存资源. 操作系统主要目的是执行程序,而程序在执行时,程序自身以及程序所访问的数据.所产生的数据都在内存里(至少所有数据的流向都会经过内存).此外,现代操作系统可以同时运行多个进程,而每个进程都有属于自己的一部分内存. 操作系统必须负责管理这些同时运行的这些进程的内存,并且还要保证进程A不会访问到进程B的内存,从而实现进程的隔离. 操作系统使用了一个称

每天3分钟操作系统修炼秘籍(8):虚拟内存分段

点我查看秘籍连载 进程的地址空间布局:分段 Linux的虚拟地址空间采用"分段+分页"结合的方式实现.先看分段,之后再介绍分页. 分段是将内存划分成各个段落(Segment),每个段落的长度可以不同,且虚拟地址空间中未使用的空间不会映射到物理内存中,所以操作系统不会为这段空间分配物理内存.这样的话,内核为刚创建的进程分配的物理内存可以很小,随着进程运行不断使用内存,内核再为进程按需分配物理内存.也就是说,尽管地址空间的范围和物理内存大小一样,但不会将全部空间映射到物理内存. 对于Lin

30天自制操作系统之第12天 定时器

定时器的中断处理程序要保证高效率,需要进行一些优化,这里介绍优化的方法.对于一个操作系统来说,会有多个定时器,假设该操作系统维护了500个定时器,当每一次定时中断发生时(这里我们设定1秒发生100次中断),调用中断处理程序,中断处理程序会对这500个定时器进行if判断,看哪些正在被使用,这样1秒内,就会有500X100=10000次if判断,而中断处理程序最讲究节省时间.实际上,我们不必每发生一次定时中断就去对这500个定时器进行判断.因为假设我们使用了500个定时器中的10个,而10个定时器中

《30天自制操作系统》笔记(12)——多任务入门

<30天自制操作系统>笔记(12)——多任务入门 进度回顾 上一篇介绍了设置显示器高分辨率的方法.本篇讲一下操作系统实现多任务的方法. 什么是多任务 对程序员来说,也许这是废话,不过还是说清楚比较好. 多任务就是让电脑同时运行多个程序(如一边写代码一边听音乐一边下载电影). 电脑的CPU只有固定有限的那么一个或几个,不可能真的同时运行多个程序.所以就用近似的方式,让多个程序轮换着运行.当轮换速度够快(0.01秒),给人的感觉就是"同时"运行了. 多任务之不实用版 我们首先从

转:攻城狮修炼秘籍

漫校园生活,孜孜不倦的你,今天书多读一点! 海康威视为你的假期精心准备了精神的饕餮大餐! 把自己投入知识的海洋吧!为即将成为一名高冷俊俏的程序猿和媛而吹响最后的号角: 各类秘籍自助区 一.测试攻城狮 <软件测试> <测试之道> 二.硬件攻城狮 基础理论:工程数学.积分变换.信号与系统.数字信号处理.自动控制原理.英语 专业课程:数电.模电.嵌入式系统.热设计.DDR3.flash.开关电源 (若有实践经验,可只看基础理论) 三.应用软件开发攻城狮 必读: <UNIX环境高级编

操作系统概念学习笔记 12 进程同步(二)管程

操作系统概念学习笔记 12 进程同步(二) 管程 基本的.高级的同步构造,即管程(monitor)类型. 使用: 管程类型提供了一组由程序员定义的.在管程内互斥的操作.管程类型的表示包括一组变量的声明(这些变量的值定义了一个类型实例的状态)和对这些变量操作的子程序和函数的实现.管程的类型表示不能直接为各个进程所使用.因此,在管程内定义的子程序只能访问位于管程内那些局部声明的变量和形式参数.类似的,管程的局部变量能被局部子程序访问. 管程结构确保一次只有一个进程能在管程内活动.不需要显示的编写同步

python3.5修炼手册12

函数 函数是组织好的,可重复使用的,用来实现单一或相关联功能的代码. 定义函数 python支持自定义函数,即由我们自己定义一个实现某个功能的函数. 自定义函数规则: ①函数代码块以def关键字开头,后接函数标识符名称和圆括号"()". ②所有传入的参数和自定义变量都必须放在圆括号中,可以在圆括号中定义参数. ③函数的第一行语句可以选择性的使用文档字符串,用于存放函数说明. ④函数内容以冒号开始,并且要缩进. ⑤return[表达式]结束函数,选择性的返回一个值给调用方.不带表达式的r

win7 安装 ubuntu 12.04 不识别分区

电脑上原来有个win7, 由于要在 ubuntu 环境下开发, 所以要装个 ubuntu . 在 win7 下, 通过压缩卷, 腾出来了 150G 的空间. 安装 ubuntu 的时候, 提示说我电脑上没有操作系统. 选择分区的地方, 看到的只有整个硬盘设备, 看不到硬盘上的分区. 网上找了些资料, 通过命令: sudo parted /dev/sda 进去后, 输入 print 提示: 可能是由不理解 GPT 分区表的程序导致的.或者您删除了 GPT 表,现在使用 msdos 分区表.这是 G