内存满了如何处理?

目录

虚拟内存

内存分配过程

直接内存回收和后台内存回收

回收内存的触发标准

那些内存被回收呢?

内存回收后,内存还是不够怎么办呢?


虚拟内存

介绍操作系统内存如何使用时,不可以避免的先认识到虚拟内存

首先我们通过虚拟内存的作用,来认识一下:

1.虚拟内存可以使得进程对运行内存超过物理内存大小,因为程序运行符合局部性原理,CPU 访问内存会有很明显的重复访问的倾向性,对于那些没有被经常使用到的内存,我们可以把它换出到物理内存之外,比如硬盘上的 swap 区域。

我们为一个进程分配内存时,分配的是一个虚拟内存,如果我们分配的是物理内存那么,当这个进程大部分东西没有被使用时,就造成了内存的浪费,所以当我们真正使用时才分配真实的物理内存

2.由于每个进程都有自己的页表,所以每个进程的虚拟内存空间就是相互独立的。进程也没有办法访问其他进程的页表,所以这些页表是私有的,这就解决了多进程之间地址冲突的问题。

物理地址是虚拟地址通过页表映射而来的,每个进程都有自己的页表,

那么每个进程访问真实的物理地址互不干扰,因为中间隔着虚拟地址

3.页表里的页表项中除了物理地址之外,还有一些标记属性的比特,比如控制一个页的读写权限,标记该页是否存在等。在内存访问方面,操作系统提供了更好的安全性。

避免了用户态直接访问内核态的物理地址

内存分配过程

直接内存回收和后台内存回收

当使用malloc动态的分配内存时,我们知道哪分配的是虚拟内存,而不是真实的物理内存

当应用程序读写了这块虚拟内存,CPU 就会去访问这个虚拟内存,

这时会发现这个虚拟内存没有映射到物理内存, CPU 就会产生缺页中断,

进程会从用户态切换到内核态,保存现场(保存PC指针)和上下文,

并将缺页中断交给 内核的缺页中断函数 处理。缺页中断处理函数会看是否有空闲的物理内存,

如果有,就直接分配物理内存,并建立虚拟内存与物理内存之间的映射关系

如果没有空闲的物理内存,那么内核就会开始进行回收内存的工作

回收的方式主要是两种:直接内存回收后台内存回收。         

后台内存回收:

后台内存回收:在物理内存紧张的时候

会唤醒 kswapd 内核线程来回收内存,这个回收内存的过程异步的,不会阻塞进程的

直接内存回收:   如果后台异步回收跟不上进程内存申请的速度,就会开始直接回收,

这个回收内存的过程是同步的,会阻塞进程的执行。(阻塞申请内存的那个进程)

影响:造成很长时间的延迟,以及系统的 CPU 利用率会升高,最终引起系统负荷飙高。

回收内存的触发标准

下面用图解释

当然你可以调整这个阈值的大小,从而尽早的运行后台内存回收,从而避免内存紧张

那些内存被回收呢?

主要有两类内存可以被回收,而且它们的回收方式也不同。

文件页:内核缓存的磁盘数据和内核缓存的文件数据都叫作文件页。

大部分文件页,都可以直接释放内存,以后有需要时,再从磁盘重新读取就可以了。

而那些被应用程序修改过,并且暂时还没写入磁盘的数据(也就是脏页),

就得先写入磁盘,然后才能进行内存释放。

所以,回收干净页的方式是直接释放内存回收脏页的方式是先写回磁盘后再释放内存


匿名页:这部分内存没有实际载体,不像文件缓存有硬盘文件这样一个载体,比如堆、栈数据等。这部分内存很可能还要再次被访问,所以不能直接释放内存,

它们回收的方式是通过 Linux 的 Swap 机制,Swap 会把不常访问的内存先写到磁盘中,

然后释放这些内存给其他更需要的进程使用。再次访问这些内存时重新从磁盘读入内存就可以了。

文件页内存页 又依靠什么机制来淘汰呢?

MySQL如何改进LRU算法-CSDN博客

哪当然是Linux的LRU,类似我这篇博客里MySQL的LRU算法,

Linux的LRU 分为两个链表 一个活跃链表, 一个非活跃链表

所以当我们 回收时 就从非活跃链表 淘汰页(把这些页从内存中淘汰,下次调用从磁盘拿)

内存回收后,内存还是不够怎么办呢?

触发 OOM (Out of Memory)机制

OOM Killer 机制会根据算法选择一个占用物理内存较高的进程,然后将其杀死,

以便释放内存资源,如果物理内存依然不足

OOM Killer 会继续杀死根据算法选择占用物理内存较高的进程,直到释放足够的内存位置。

算法:

1. 进程使用的物理内存量:

// points 代表打分的结果
// process_pages 代表进程已经使用的物理内存页面数
// oom_score_adj 代表 OOM 校准值
// totalpages 代表系统总的可用页面数
points = process_pages + oom_score_adj*totalpages/1000

2.特权进程的评分:特权进程通常较为重要,因此将其得分设置为1/4。例如守护进程  (1号进程)

  • 13
    点赞
  • 18
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值