本文主要分析 linux 系统内存统计的一些指标以及进程角度内存使用监控的一些方法 。
开始阅读这篇文章前,请先简单阅读下面的几篇文章 。
- 《进程眼中的线性地址空间》
- 《线程眼中的线性地址空间》
- 《聊聊内存管理》
从 free 命令开始上面的背景介绍文章把内存相关的基础概念讲的差不多了,这里不再赘述 。本文定位是内存统计,所以从最基础的内存统计的命令—
free
命令开始 。执行free
命令,可以看到如下的输出:文章插图
纵向是内存和
Swap
分区,横向是统计项 。纵向的含义以及Swap
不需要解释,我们看横向的统计项:- total — 系统总内存(其实就是从
/proc/meminfo
获取的)
- used — 已使用内存
- free — 未使用的内存
- shared — 共享内存的大小,主要是
tmpfs
- buff / cache —
buffers
和cache
使用的内存之和
- available — 可用内存,可以简单理解为未使用的内存和可释放的内存之和(buffer、cache 可以释放大部分,所以这里近似等于 free + buffer / cache 的大小)
free
命令的输出是这样:文章插图
这里的
shared
为0,因为这台服务器没用共享内存 。这里多解释下-/+ buffer/cache
这行,字面意思就是used - buffers/cache
和used + buffers/cache
。前者指的是从应用程序角度系统被用掉了多少内存,后者指的是从应用程序角度看系统还有多少内存能用 。听起来很复杂,其实说白了就是因为buffers
和cached
可以被释放出来,多几个指标看看系统还能用多少内存而已 。下面用几个公式来解释这个输出:
1234567891011# 内存总量 = 已使用内存 + 空闲内存`total` = `used` + `free`# 系统被用掉的内存`-buffers/cache` = `used` - `buffers` - `cached`# 系统还能用的内存`+buffers/cache` = `free` + `buffers` + `cached`# 所以,其实还有下面的公式`total` = `-buffers/cache` + `+buffers/cache`
buffers/cached
不是100%都能释放出来使用的,上面的“可用内存”其实就是个近似值 。最上面新版本系统的输出中有一个available
项目表示可用内存,值小于free + buff/cache
,内核 3.14 之后支持该特性(虽然也不是绝对意义上的精确的可用内存大小,囧) 。这里稍微多说一点
buffers
和cached
。Linux 2.4.10 内核之前,磁盘的缓存有两种,即Buffer Cache
和Page Cache
。前者缓存管理磁盘文件系统时读取的块,后者存放访问具体文件内容时生成的页 。在 2.4.10 之后,Buffer Cache
这个概念就不存在了,这些数据被放在Page Cache
中(这种Page
被称为Buffer Pages
) 。简而言之,现在磁盘的 cache 只有
Page Cache
一种,在Page Cache
中,有一种Page
叫Buffer Page
,这种Page
都与一个叫buffer_head
的数据结构关联,这些页也就在内存统计中用buffers
这个指标来单独统计了 。/proc/meminfo 详解很多命令的内存统计都是从
/proc/meminfo
读取的 。鉴于/proc/meminfo
的 man 文档(man proc
)写的实在不够清晰,很多条目居然还是To be documented
状态,所以这里逐一列举出来常见的统计项解释一下 。首先明确一点,内核目前并没有绝对精确的统计所有的内存使用量,比如
alloc_pages
接口申请的内存不一定被统计在内(除非所有调用alloc_pages
的代码主动进行统计,如果某些不讲究的驱动程序没有主动统计的话统计值就肯定对不上了) 。先看这三项全局统计: