page fault带来的性能问题

本文涉及的产品
云原生数据库 PolarDB 分布式版,标准版 2核8GB
RDS PostgreSQL Serverless,0.5-4RCU 50GB 3个月
推荐场景:
对影评进行热评分析
云数据库 RDS SQL Server,基础系列 2核4GB
简介: Linux进程如何访问内存 Linux下,进程并不是直接访问物理内存,而是通过内存管理单元(MMU)来访问内存资源。原因后面会讲到。 为什么需要虚拟内存地址空间 假设某个进程需要4MB的空间,内存假设是1MB的,如果进程直接使用物理地址,这个进程会因为内存不足跑不起来。既然进程不是直接访问

Linux进程如何访问内存

Linux下,进程并不是直接访问物理内存,而是通过内存管理单元(MMU)来访问内存资源。
原因后面会讲到。

为什么需要虚拟内存地址空间

假设某个进程需要4MB的空间,内存假设是1MB的,如果进程直接使用物理地址,这个进程会因为内存不足跑不起来。
既然进程不是直接访问物理内存,那么进程中涉及的内存地址当然也不是物理内存地址。
而是虚拟的内存地址,虚拟的内存地址和物理的内存地址之间保持一种映射关系,这种关系由MMU进行管理。
每个进程都有自己独立的虚拟地址空间。

什么是MMU

MMU_principle_updated
MMU全称是内存管理单元,它将物理内存分割成多个pages,MMU管理进程的虚拟地址空间中的PAGE和物理内存中的PAGE之间的映射关系。
因为是映射,所以随时都可能发生变化,例如某个进程虚拟内存空间中的PAGE1,在不同的时间点,可能出现在物理内存中的不同位置(当发生了页交换时)。

什么是page fault

当进程访问它的虚拟地址空间中的PAGE时,如果这个PAGE目前还不在物理内存中,此时CPU是不能干活的,
Linux会产生一个hard page fault中断。
系统需要从慢速设备(如磁盘)将对应的数据PAGE读入物理内存,并建立物理内存地址与虚拟地址空间PAGE的映射关系。
然后进程才能访问这部分虚拟地址空间的内存。

page fault 又分为几种,major page fault、 minor page fault、 invalid(segment fault)。

major page fault也称为hard page fault, 指需要访问的内存不在虚拟地址空间,也不在物理内存中,需要从慢速设备载入。从swap回到物理内存也是hard page fault。

minor page fault也称为soft page fault, 指需要访问的内存不在虚拟地址空间,但是在物理内存中,只需要MMU建立物理内存和虚拟地址空间的映射关系即可。
(通常是多个进程访问同一个共享内存中的数据,可能某些进程还没有建立起映射关系,所以访问时会出现soft page fault)

invalid fault也称为segment fault, 指进程需要访问的内存地址不在它的虚拟地址空间范围内,属于越界访问,内核会报segment fault错误。

什么是进程的working set

进程的working set是指当前在物理内存中,属于该进程的pages组成的集合。
这个集合中的page数随着系统的运行,可能扩大也可能缩小。
扩大working set是指进程正在访问更多的内存时。
缩小working set是指其他进程正在访问更多的内存,并且整个物理内存的空间不足,需要将某些干净的内存页free掉或者一些脏的内存页swap到交换分区去,如果这个操作设计到当前进程,对当前进程来说就是shrink working set。
缩小working set需要遵循lru (内核的内存老化)算法,并不是随便挑选PAGE进行shrink的。

什么是swap

swap和前面提到的shrink working set有关,如果是干净页(即从读入虚拟地址空间后,没有修改过的页),则直接标记为free,不需要写盘,也不会发生swap。
如果是脏页,那么它需要写盘,或者需要swap 到交换分区。

如何优化swap

建议使用IOPS和读写带宽很高的盘作为SWAP分区,例如PCI-E SSD。

什么时候需要加内存

如果你发现经常发生swap in , out。
说明进程的脏页被换出到swap后,紧接着这些页可能又需要被进程访问,从而这些页需要从swap写入物理内存,发生了hard page fault。
这种情况下,你就需要加内存了,确实是内存不够用了。
hard page fault非常损耗性能,因为发生page fault时,是需要等待的,而且IO通常来说都是比较慢的,容易成为性能瓶颈。

什么是oom, 为什么会发生OOM

前面讲到了shrink working set,是指系统在内存调度时,使用的一种手段,尽可能的让系统能使用有限的内存资源,支撑更多的并发任务。
oom是指系统已经没有足够的内存给进程使用,即能free的都已经free了,能swap out的也已经swap out了,再也不能挤出物理内存的情况。
如果遇到这种情况就会发生OOM,表示系统内存以及不足,Linux会挑选并KILL一些进程,来释放内存。

Linux page相关统计信息

sar

       -B     Report paging statistics.  The following values are displayed:

              pgpgin/s
                     Total number of kilobytes the system paged in from disk per second.

              pgpgout/s
                     Total number of kilobytes the system paged out to disk per second.

              fault/s
                     Number of page faults (major + minor) made by the system per second.  This is not a count of page faults that generate I/O, because some page faults can be resolved without I/O.

              majflt/s
                     Number of major faults the system has made per second, those which have required loading a memory page from disk.

              pgfree/s
                     Number of pages placed on the free list by the system per second.

              pgscank/s
                     Number of pages scanned by the kswapd daemon per second.

              pgscand/s
                     Number of pages scanned directly per second.

              pgsteal/s
                     Number of pages the system has reclaimed from cache (pagecache and swapcache) per second to satisfy its memory demands.

              %vmeff
                     Calculated as pgsteal / pgscan, this is a metric of the efficiency of page reclaim. If it is near 100% then almost every page coming off the tail of the inactive list is being reaped. If it gets too  low  (e.g.
                     less than 30%) then the virtual memory is having some difficulty.  This field is displayed as zero if no pages have been scanned during the interval of time.

一些CASE

.1. 如果PostgreSQL 设置了非常大的shared buffer, 为什么会有一段性能低潮(指全力压测时,平时估计感觉不到)
在PostgreSQL shared buffer设得非常大的情况下,Shared buffer作为进程的虚拟地址空间中的一部分,刚启动时这些虚拟地址空间还没有在物理内存中,所以填充过程中会发生page fault,性能较低。
当shared buffer被快速填满后,page fault减少,性能会上来。
例如在压测持续高并发的COPY数据入库时,看这个case https://yq.aliyun.com/articles/8528
在前面几百GB,page fault较多,产生较多的中断(这个case是软的,因为是在shared buffer中进行extend block,么有落盘),性能比shared buffer填满后有一定的差异。
240GB shared buffer,
shared buffer 填满前,2.8GB/s 导入速度

12:13:46 AM  pgpgin/s pgpgout/s   fault/s  majflt/s  pgfree/s pgscank/s pgscand/s pgsteal/s    %vmeff
12:13:47 AM      8.08 1699410.10  40058.59      0.00 142064.65 137696.97      0.00 137632.32     99.95
12:13:48 AM     15.84 1634396.04  38605.94      0.00 412391.09 411564.36      0.00 411627.72    100.02

 22  44  33   0   0   0|  32k 2763M| 239B  364B|   0     0 | 184k  335k
 22  44  34   0   0   0|  12k 2791M| 120B  544B|   0     0 | 184k  336k
 22  45  33   0   0   0|  12k 2768M| 471B 1198B|   0     0 | 185k  341k
 22  44  33   0   0   0|  16k 2764M| 210B  454B|   0     0 | 183k  336k
 22  44  34   0   0   0|  16k 2777M| 239B  364B|   0     0 | 185k  341k

shared buffer 填满后, 4.7GB/s导入速度

12:14:40 AM  pgpgin/s pgpgout/s   fault/s  majflt/s  pgfree/s pgscank/s pgscand/s pgsteal/s    %vmeff
12:14:41 AM     16.33 2831730.61    823.47      0.00 735045.92 725126.53      0.00 724985.71     99.98
12:14:42 AM     12.00 2760160.00    743.00      0.00 738037.00 728352.00      0.00 728370.00    100.00
12:14:43 AM     11.88 2751279.21    326.73      0.00 720171.29 715310.89      0.00 715374.26    100.01
12:14:44 AM     20.00 2788468.00    338.00      0.00 727221.00 720480.00      0.00 720480.00    100.00
12:14:45 AM     12.50 2858970.83    425.00      0.00 753507.29 740266.67      0.00 740166.67     99.99

 24  18  56   0   0   1|  28k 4703M| 120B  364B|   0     0 | 366k  655k
 24  18  57   0   0   1|  16k 5031M| 892B  994B|   0     0 | 382k  690k
 24  19  56   0   0   0|  12k 4833M| 120B  364B|   0     0 | 374k  672k
 24  19  56   0   0   1|8192B 4737M| 239B  544B|   0     0 | 371k  668k
 24  19  56   0   0   1|  20k 4826M| 120B  454B|   0     0 | 375k  674k

参考

目录
相关文章
|
Linux 数据安全/隐私保护 Perl
bpf对内核的观测
bpftrace 可以对线上项目的系统调用的函数的进行观测,对观测的结果做出分析
293 0
|
监控 调度 开发工具
IO神器blktrace使用介绍
## 前言 1. blktrace的作者正是block io的maintainer,开发此工具,可以更好的追踪IO的过程。 2. blktrace 结合btt可以统计一个IO是在调度队列停留的时间长,还是在硬件上消耗的时间长,利用这个工具可以协助分析和优化问题。 ## blktrace的原理 一个I/O请求的处理过程,可以梳理为这样一张简单的图: ![](http://image
19625 0
|
负载均衡 Java 应用服务中间件
微服务分布式系统架构之zookeeper与dubbor-1
微服务分布式系统架构之zookeeper与dubbor-1
|
前端开发 Java 容器
Java一分钟之-JavaFX控件:Button, TextField, Label等
JavaFX教程概述了构建UI的基本控件:Button用于用户操作,TextField提供文本输入,Label显示静态文本。文章讨论了样式、事件处理和布局管理常见问题及其解决方案,并提供了一个使用这些控件创建简单应用的代码示例,强调实践中提升GUI开发技能的重要性。
412 1
|
11月前
|
消息中间件 存储 Java
Kafka核心知识点整理,收藏再看!
Kafka核心知识点整理,收藏再看!
198 3
Kafka核心知识点整理,收藏再看!
|
11月前
|
机器学习/深度学习 存储 人工智能
用60%成本干80%的事,DeepSeek分享沉淀多年的高性能深度学习架构
【10月更文挑战第2天】近年来,深度学习(DL)与大型语言模型(LLMs)的发展推动了AI的进步,但也带来了计算资源的极大需求。为此,DeepSeek团队提出了Fire-Flyer AI-HPC架构,通过创新的软硬件协同设计,利用10,000个PCIe A100 GPU,实现了高性能且低成本的深度学习训练。相比NVIDIA的DGX-A100,其成本减半,能耗降低40%,并在网络设计、通信优化、并行计算和文件系统等方面进行了全面优化,确保系统的高效与稳定。[论文地址](https://arxiv.org/pdf/2408.14158)
613 4
|
SQL 关系型数据库 数据库
PostgreSQL 如何潇洒的处理每天上百TB的数据增量
本文主要介绍并测试一下PostgreSQL 在中高端x86服务器上的数据插入速度,帮助企业用户了解PostgreSQL在这种纯插入场景的性能。(例如运营商网关数据,金融行业数据,产生量大,并且要求快速插入大数据库中持久化保存。) 测试结果写在前面:每32K的block存储89条记录, 每条记录约3
39620 131
|
存储 缓存 网络协议
2.8 基于DPDK的UDP用户态协议栈实现
2.8 基于DPDK的UDP用户态协议栈实现
567 0
|
关系型数据库 MySQL 程序员
程序员性能之道,从使用perf开始!
程序员性能之道,从使用perf开始!