Linux系统释放buff/cache内存

一直都没怎么关注buff/cache这个部分,因为平时在服务器上使用的过程中内存是够用的。但是最近在部署应用的时候发现内存已经严重不够用的,只剩100多M,使用top命令一看,buff/cache占用了好多内存,几乎是这个剩余空间的4-5倍。如下所示:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
top - 16:20:24 up 11 days, 11 min,  2 users,  load average: 0.00, 0.16, 0.60
Tasks: 101 total, 1 running, 99 sleeping, 0 stopped, 1 zombie
%Cpu(s): 0.7 us, 0.3 sy, 0.0 ni, 98.8 id, 0.2 wa, 0.0 hi, 0.0 si, 0.0 st
KiB Mem : 3881688 total, 102556 free, 3322056 used, 457076 buff/cache
KiB Swap: 0 total, 0 free, 0 used. 334948 avail Mem

PID USER PR NI VIRT RES SHR S %CPU %MEM TIME+ COMMAND
1324 rabbitmq 20 0 1146304 44220 1092 S 0.7 1.1 0:18.66 beam.smp
7733 conflue+ 20 0 4009488 1.490g 40692 S 0.3 40.2 2:39.05 java
8069 conflue+ 20 0 3704192 566552 16588 S 0.3 14.6 0:23.80 java
21814 redis 20 0 151104 11028 208 S 0.3 0.3 0:46.42 redis-server
21892 root 20 0 136668 10980 980 S 0.3 0.3 10:22.68 AliYunDun
1 root 20 0 190716 2380 1156 S 0.0 0.1 0:06.98 systemd
2 root 20 0 0 0 0 S 0.0 0.0 0:00.04 kthreadd

我觉得这部分空间还是可以利用一下的,首先来看看这部分空间主要的作用。

buff/cache是什么

cache只是用来缓存文件的,经常读写的文件会被缓存到cache中,可以增加读写效率,该功能是Linux系统内核提供的。也就是说为了避免频繁地发生IO请求,可以先将一部分数据写入到buffer/cache中然后再批量地持久化到本地的磁盘上。那么buffer和cache有什么区别呢?首先从字面上来说,一个是缓冲(buffer),另一个是缓存(cache),作用区别应该比较明显了。下面是一个对照表:

buff cache
Buffer:缓冲区,用于存储速度不同步的设备或优先级不同的设备之间传输数据;通过buffer可以减少进程间通信需要等待的时间,当存储速度快的设备与存储速度慢的设备进行通信时,存储慢的数据先把数据存放到buffer,达到一定程度存储快的设备再读取buffer的数据,在此期间存储快的设备CPU可搜索以干其他的事情。 Cache:缓存区,是高速缓存,是位于CPU和主内存之间的容量较小但速度很快的存储器,因为CPU的速度远远高于主内存的速度,CPU从内存中读取数据需等待很长的时间,而 Cache保存着CPU刚用过的数据或循环使用的部分数据,这时从Cache中读取数据会更快,减少了CPU等待的时间,提高了系统的性能。
Buffer:一般是用在写入磁盘的,例如:某个进程要求多个字段被读入,当所有要求的字段被读入之前已经读入的字段会先放到buffer中。 Cache并不是缓存文件的,而是缓存块的(块是I/O读写最小的单元);Cache一般会用在I/O请求上,如果多个进程要访问某个文件,可以把此文件读入Cache中,这样下一个进程获取CPU控制权并访问此文件直接从Cache读取,提高系统性能。

内存释放脚本

释放这部分内存的方式Linux内核团队也给出了说明,主要分为三条命令。

  • echo 1 > /proc/sys/vm/drop_caches //To free pagecache.
  • echo 2 > /proc/sys/vm/drop_caches //To free dentries and inodes.
  • echo 3 > /proc/sys/vm/drop_caches //To free pagecache,dentries and inodes.

在运行这三条命令之前,需要把存在于缓冲区和缓存区的数据持久化到磁盘当中去,需要使用到sync命令。因此,整个内存释放的脚本可以写为:

1
2
3
4
5
6
7
8
9
#! /bin/sh
used=`free -m | awk 'NR==2' | awk '{print $3}'`
free=`free -m | awk 'NR==2' | awk '{print $4}'`

if [ $free -le 200 ] ; then
sync && echo 1 > /proc/sys/vm/drop_caches
sync && echo 2 > /proc/sys/vm/drop_caches
sync && echo 3 > /proc/sys/vm/drop_caches
fi

将文件命名为release_cache.sh,使用crontab -e写入到一个定时任务中,每隔5分钟检查一次内存使用情况,如果可用空间小于这个值,就释放内存:

1
*/5 * * * * /root/wiki_ops/release_cache.sh

总结

buff/cache这部分内存正常情况下只要不影响常规应用的使用就不需要关注它的内存占用情况,但是如果出现剩余空间严重不足,而buff/cache空间占用特别高的情况下就需要定时清理这部分内存空间了。

分享到