事实上,当上述服务器系统资源中的任何一个遭遇瓶颈,都会带来服务器性能的下降,典型的症状就是系统运行迟缓。
本文从以下几个角度介绍Linux系统内存相关的排查。
- 内存的使用率如何查看,使用率真的很高吗
- 内存用在哪里了
- 内存优化可以有哪些手段
内存硬件查看
在Linux系统环境下,可以使用dmidecode命令查看硬件设备的详细信息。
命令格式: dmidecode -t typecode
其中typecode是设备类型代码, 具体代码如下:
0 BIOS
1 System
2 Base Board
3 Chassis
4 Processor
5 Memory Controller
6 Memory Module
7 Cache
8 Port Connector
9 System Slots
10 On Board Devices
11 OEM Strings
12 System Configuration Options
13 BIOS Language
14 Group Associations
15 System Event Log
16 Physical Memory Array
17 Memory Device
18 32-bit Memory Error
19 Memory Array Mapped Address
20 Memory Device Mapped Address
21 Built-in Pointing Device
22 Portable Battery
23 System Reset
24 Hardware Security
25 System Power Controls
26 Voltage Probe
27 Cooling Device
28 Temperature Probe
29 Electrical Current Probe
30 Out-of-band Remote Access
31 Boot Integrity Services
32 System Boot
33 64-bit Memory Error
34 Management Device
35 Management Device Component
36 Management Device Threshold Data
37 Memory Channel
38 IPMI Device
39 Power Supply
例如:
使用dmidecode -t 1 可以查看主板信息(制造商、型号、序列号等等)
使用dmidecode -t 4 可以查看CPU信息(CPU数据、型号、大小、频率等等)
使用dmidecode -t 17 可以查看内存信息(插槽数目、内存类型、大小、频率等等)
通过dmidecode工具可以查看很多硬件相关的数据,这里仅以内存为例。我们可以看到,服务器最大支持内存扩充为4GB,目前已经安装了4GB内存。
内存的使用情况
使用free命令可以查看内存的使用情况。
-m以MB为单位显示整个系统的使用情况:
-h则自动选择以适合理解的容量单位显示:
可以看到系统内存4G(总可用3.9G),当前医用3.8G,剩余103M。命令显示的”used”的值很高,接近total的值了,那么系统就真的没有内存空间了吗?
我们可以看到free命令下面有一行“-/+ buffers/cache”,该行显示的used是上一行“used”的值减去buffers和cached的值,同时该行的free是上一行的free加上buffers和cached的值。这里可以看到,尽管第一行的used显示共使用了3.8GB的物理内存,但除去buffers和cached数据后,实际仅仅占用了631M的内存,而如果剩余空间加上buffers和cached数据当前占用的内存,将达到3.2BG。
这是因为buffers和cache数据是动态变化的,内存充足时,内核出于性能考虑会进行一定的缓存,当内存空间不足时,buffers, cached占用的空间是可以为了程序释放的。
因此判断系统内存是否耗竭的实际指标是看减去buffer和cache的空间后used空间是否依旧很大,以及交换空间是否被大量占用。显然这个例子不符合内存耗竭的情形。
查看消耗内存较多的内存
top 命令用来查看具体进程消耗的内存空间
top 命令查看系统的实时负载,包括进程、CPU负载、内存使用等等;
进入top的实时界面后,默认按照CPU的使用率排序,通过”shift+m”将进程按照内存使用情况排序,可以查看哪些进程是当前系统的内存开销”大户”。
top 命令中,按下f键,进入选择排序的界面,可以选择要显示的信息列,要按照哪些信息列进行排序等,该界面上有简要的介绍。
另一方面,我们查看不同进程的内存开销:
通过%MEM列,可以查看哪几个进程占用了大量的内存,在缓解内存不足的紧急情况时,可以终止这些占用内存较多的进程。
top 命令中有一下与内存相关的数据列:
(1)VIRT:虚拟内存,是进程身亲的虚拟内存总量。
(2)RES: 常驻内存,是进程切实使用的物理内存量,free命令中看到的used列下面的值,就包括常驻内存的和,但不是虚拟内存的和。
(3)SHR: 共享内存,比如共享占用的内存等。
交换空间
使用free 命令可以查看内存的总体使用,显示的内容也包括交换分区的大小,使用swapon、swapoff命令开启或关闭交换空间,交换空间是磁盘上的文件,并不是真正的内存空间。
当内存不足时,系统会选择通过: 1.将部分不常被访问的内存页交换到内存空间; 2.删除部分cache 的文件来释放内存空间。
系统的可用内存一般等于物理内存+交换分区。交换分区在磁盘上,因此速度比内存读写要慢的多。
交换分区实际上就是磁盘上的文件,可以通过mkswap 命令创建交换空间。
内核态内存占用
slab系统用来处理系统中比较小的元数据,如文件描述符等,进而组织内核态的内存分配。
一个slab包含多个object,例如dentry这些数据结构就是object,可以通过slabtop命令查看系统中活动的object的数量与内存占用情况,从而了解哪些数据结构最占用内核态的内存空间。
例如: 使用slabtop 命令查看内核数据结构及内存占用
关注点:
1. 哪些数据结构的内存占用最大
2. 哪些类型的数据结构对应的object最多,比如inode多代表文件系统被大量引用等。
该交互命令支持的选项与排序标准有:
选项:
--delay=n, -d n 每隔n秒刷新信息
--once, -o 只显示一次
--sort=S, -s S 按照S排序,其中S为排序标准
排序标准(shift + 对应的键):
a:根据active objects数量高低排序
b:根据 objects / slab高低来排序
c:根据cache大小排序
l:根据slab数量排序
v:根据active slabs数量排序
n:按 name 排序
o:按照 objects 数量排序
p:按照 pages / slab 的值排序
s:按照 object 大小排序
u:按照 cache 使用量排序
查看内存使用的动态变化
vmstat命令可以查看内存使用的动态变化
每行会输出一些系统核心指标,这些指标可以让我们更详细的了解系统状态。后面跟的参数1,表示每秒输出一次统计信息,表头提示了每一列的含义,这几介绍一些和性能调优相关的列:
r:等待CPU资源的进程数。这个数据比平均负载更加能够体现CPU负载情况,数据中不包含等待IO的进程。如果这个数值大于机器CPU核数,那么机器的CPU资源已经饱和。
free:系统可用内存数(以千字节为单位),如果剩余内存不足,也会导致系统性能问题。
si, so:交换区写入和读取的数量。如果这个数据不为0,说明系统已经在使用交换区(swap),机器物理内存已经不足。
us, sy, id, wa, st:这些都代表了CPU时间的消耗,它们分别表示用户时间(user)、系统(内核)时间(sys)、空闲时间(idle)、IO等待时间(wait)和被偷走的时间(stolen,一般被其他虚拟机消耗)。
dstat
dstat命令是一个用来替换vmstat、iostat、netstat、nfsstat和ifstat这些命令的工具,是一个全能系统信息统计工具。与sysstat相比,dstat拥有一个彩色的界面,在手动观察性能状况时,数据比较显眼容易观察;而且dstat支持即时刷新,譬如输入dstat 3即每三秒收集一次,但最新的数据都会每秒刷新显示。和sysstat相同的是,dstat也可以收集指定的性能资源,譬如dstat -c即显示CPU的使用情况。
查看共享内存空间
pmap 命令用于报告进程的内存映射关系,是Linux调试及运维一个很好的工具。
常用选项:
-x: 显示扩展格式
-d: 显示设备格式
-q: 不显示头尾行
-V: 显示指定版本
参数:
进程号: 制定需要显示内存映射关系的进程号,可以是多个进程号
查看系统内存历史记录
sar(System Activity Reporter系统活动情况报告) 是目前Linux上最为全面的系统性能分析工具之一。可以从多方面对系统的活动进行报告,包括:文件的读写情况、系统调用的使用情况、磁盘I/O、CPU效率、内存使用状况、进程活动及IPC有关的活动等。
命令格式:
sar [options] [-A] [-o file] t [n]
其中:
t 为采样间隔,n为采样次数,默认值是1
-o file 表示将命令结果以二进制格式存放在文件中,file是文件名
options 为命令行选项,命令常用选项:
-A: 所有报告的总和
-u: 输出CPU使用情况的统计信息
-v: 输出inode、文件和其他内核表的统计信息
-d: 输出每一块设备的活动信息
-r: 输出内存和交换空间的统计信息
-b: 显示I/O和传送速率的统计信息
-a: 文件读写情况
-c: 输出进程统计信息,每秒创建的进程数
-R: 输出内存页面的统计信息
-y: 终端设备活动情况
-w: 输出系统交换活动信息
如何清理内存使用
释放占用的缓存空间
# sync //先将内存刷出,避免数据丢失
# echo 1 > /proc/sys/vm/drop_caches //释放pagecache
# echo 2 > /proc/sys/vm/drop_caches //释放dentry和inode
# echo 3 > /proc/sys/vm/drop_caches //释放pagecache、dentry和inode终止进程
与Linux内存相关的文件系统文件
内存信息: /proc/meminfo
进程状态信息: /proc/$pid/status
进程物理内存信息: /proc/$pid/statm
slab的分布情况: /proc/slabinfo
虚拟内存信息: /proc/vmstat
小福利
降低swap的使用率:
# sysctl -a | grep swappiness
vm.swappiness = 60限制其他用户的内存使用:
# vim /etc/security/limits.conf
user1 hard as 1000 (用户user1所有累加起来,内存不超过1000kiB)
user1 soft as 800 (用户user1一次运行,内存不超过800kiB)大量连续内存数据:
# vim /etc/sysctl.conf
vm.nr_hugepage=20调节page cache(大量一样的请求 调大page cache)
vm.lowmem_reserve_ratio = 256 256 32 (保留多少内存作为pagecache 当前 最大 最小)
vm.vfs_cache_pressure=100 (大于100,回收pagecache)
vm.page.cluster=3(一次性从swap写入内存的量为2的3次方页)
vm.zone_reclaim_mode=0/1(当内存危机时,是否尽量回收内存 0:尽量回收 1:尽量不回收)
min_free_kbytes:该文件表示强制Linux VM最低保留多少空闲内存(Kbytes)。脏页
vm.dirty_background_radio=10 (当脏页占内存10%,pdflush工作)
vm.dirty_radio=40 (当进程自身脏页占内存40%,进程自己处理脏页,将其写入磁盘)
vm.dirty_expire_centisecs=3000 (脏页老化时间为30秒 3000/100=30秒)
vm.dirty_writeback_centisecs=500 (每隔5秒,pdflush监控一次内存数量 500/100=5秒)