`

liunx的Slab占用比较高的问题

阅读更多

最近经常报内存超过80%的阀值.

统计了下内存实际使用只有1.6G,希望能帮我们分析下为什么内存的使用率显示使用了3178M.

 

-bash-3.2$ ps -eo 'pid,rss' --sort=-rss
(Not all processes could be identified, non-owned process info
 will not be shown, you would have to be root to see it all.)
  PID   RSS
20872 732320
 5030 617408
15583 219672
15320 15940
 9654 10088
 1846  9100
 8580  8748
 9665  8588
 3938  8304
 2711  3996
 8575  3276
 7753  3260
19912  2464
 2689  2140
14368  2036
28490  1968
 2690  1800
 7755  1748
 7756  1568
 2049  1548
 2429  1480
 1841  1304
 2588  1304
23519  1212
23559  1176
 2687  1052
 8587  1048
 8592  1040
 2386   888
 1897   864
 8593   856
 1833   808
 8588   804
 8594   740
 8590   736
29128   672
 2526   652
    1   648
 1842   648
 1788   584
 1946   572
 1864   568
 1856   556
 1806   448
 2558   416
 2559   416
 2562   416
 2585   416
 2586   416
 2587   416
  450   368
 1791   332
 2405   284
    2     0
    3     0
    4     0
    5     0
    6     0
    7     0
    8     0
    9     0
   10     0
   45     0
   50     0
   51     0
   52     0
   97     0
   98     0
  101     0
  103     0
  177     0
  180     0
  181     0
  182     0
  318     0
  331     0
  332     0
  360     0
  361     0
  362     0
  372     0
  391     0
  417     0
 1339     0
 1340     0
 1341     0
 1368     0
 6460     0
 6468     0
 
然后统计 rss列的内存总数是1,680M 远小于显示使用的3G.请问那部分内存被什么程序占用了?
确认应用进程占用内存不多,可以安装工具atop,或者执行命令cat /proc/meminfo |grep -i slab看看slab占用的内存是否较多。


 
SLAB是Linux操作系统的一种内存分配机制。其工作是针对一些经常分配并释放的对象,您可以看看哪些应用进程的slab占用的内存比较多,是否这些应用需要频繁的请求和释放内存,比如进行一些小文件的读写。如果都是应用的正常使用,可以考虑升级服务器内存,如果内存不足影响业务,需要临时释放一下slab占用的内存,
可以参考以下步骤: #echo 2 > /proc/sys/vm/drop_caches
等内存回收完毕后再 #echo 0 > /proc/sys/vm/drop_caches
其中drop_caches的4个值有如下含义:
0:不做任何处理,由系统自己管理 1:清空pagecache 2:清空dentries和inodes 3:清空pagecache、dentries和inodes
 
--------------------------------------------------

问题描述

Linux服务器内存使用量超过阈值,触发报警。

问题排查

首先,通过free命令观察系统的内存使用情况,显示如下:

  1. total       used       free     shared    buffers     cached 
  2. Mem:      24675796   24587144      88652          0     357012    1612488 
  3. -/+ buffers/cache:   22617644    2058152 
  4. Swap:      2096472     108224    1988248 

其中,可以看出内存总量为24675796KB,已使用22617644KB,只剩余2058152KB。

然后,接着通过top命令,shift + M按内存排序后,观察系统中使用内存最大的进程情况,发现只占用了18GB内存,其他进程均很小,可忽略。

因此,还有将近4GB内存(22617644KB-18GB,约4GB)用到什么地方了呢?

进一步,通过cat /proc/meminfo发现,其中有将近4GB(3688732 KB)的Slab内存:

  1. ...... 
  2. Mapped:          25212 kB 
  3. Slab:          3688732 kB 
  4. PageTables:      43524 kB 
  5. ...... 

Slab是用于存放内核数据结构缓存,再通过slabtop命令查看这部分内存的使用情况:

  1. OBJS ACTIVE  USE OBJ SIZE  SLABS OBJ/SLAB CACHE SIZE NAME 
  2. 13926348 13926348 100%    0.21K 773686       18   3494744K dentry_cache 
  3. 334040 262056  78%    0.09K   8351       40     33404K buffer_head 
  4. 151040 150537  99%    0.74K  30208        5    120832K ext3_inode_cache 

发现其中大部分(大约3.5GB)都是用于了dentry_cache。

问题解决

1. 修改/proc/sys/vm/drop_caches,释放Slab占用的cache内存空间(参考drop_caches的官方文档):

  1. Writing to this will cause the kernel to drop clean caches, dentries and inodes from memory, causing that memory to become free. 
  2. To free pagecache: 
  3. * echo 1 > /proc/sys/vm/drop_caches 
  4. To free dentries and inodes: 
  5. * echo 2 > /proc/sys/vm/drop_caches 
  6. To free pagecache, dentries and inodes: 
  7. * echo 3 > /proc/sys/vm/drop_caches 
  8. As this is a non-destructive operation, and dirty objects are notfreeable, the user should run "sync" first in order to make sure allcached objects are freed. 
  9. This tunable was added in 2.6.16. 

2. 方法1需要用户具有root权限,如果不是root,但有sudo权限,可以通过sysctl命令进行设置:

  1. $sync 
  2. $sudo sysctl -w vm.drop_caches=3 
  3. $sudo sysctl -w vm.drop_caches=0 #recovery drop_caches 

操作后可以通过sudo sysctl -a | grep drop_caches查看是否生效。

3. 修改/proc/sys/vm/vfs_cache_pressure,调整清理inode/dentry caches的优先级(默认为100),LinuxInsight中有相关的解释:

  1. At the default value of vfs_cache_pressure = 100 the kernel will attempt to reclaim dentries and inodes at a “fair” rate with respect to pagecache and swapcache reclaim. Decreasing vfs_cache_pressure causes the kernel to prefer to retain dentry and inode caches. Increasing vfs_cache_pressure beyond 100 causes the kernel to prefer to reclaim dentries and inodes.  

具体的设置方法,可以参考方法1或者方法2均可。

参考资料

  • https://www.kernel.org/doc/Documentation/sysctl/vm.txt
  • http://major.io/2008/12/03/reducing-inode-and-dentry-caches-to-keep-oom-killer-at-bay/
  • http://linux-mm.org/Drop_Caches

以下记录的是进一步排查的进展情况。

更深层次的原因

上文排查到Linux系统中有大量的dentry_cache占用内存,为什么会有如此多的dentry_cache呢?

1. 首先,弄清楚dentry_cache的概念及作用:目录项高速缓存,是Linux为了提高目录项对象的处理效率而设计的;它记录了目录项到inode的映射关系。因此,当应用程序发起stat系统调用时,就会创建对应的dentry_cache项(更进一步,如果每次stat的文件都是不存在的文件,那么总是会有大量新的dentry_cache项被创建)。

2. 当前服务器是storm集群的节点,首先想到了storm相关的工作进程,strace一下storm的worker进程发现其中有非常频繁的stat系统调用发生,而且stat的文件总是新的文件名:

sudo strace -fp <pid> -e trace=stat

3. 进一步观察到storm的worker进程会在本地目录下频繁的创建、打开、关闭、删除心跳文件,每秒钟一个新的文件名:

sudo strace -fp <pid> -e trace=open,stat,close,unlink

以上就是系统中为何有如此多的dentry_cache的原因所在。

一个奇怪的现象

通过观察/proc/meminfo发现,slab内存分为两部分:

SReclaimable // 可回收的slab
SUnreclaim // 不可回收的slab

当时服务器的现状是:slab部分占用的内存,大部分显示的都是SReclaimable,也就是说可以被回收的。

但是通过slabtop观察到slab内存中最主要的部分(dentry_cache)的OBJS几乎都是ACTIVE的,显示100%处于被使用状态。

OBJS ACTIVE  USE OBJ SIZE  SLABS OBJ/SLAB CACHE SIZE NAME                   
13926348 13926348 100%    0.21K 773686       18   3494744K dentry_cache
334040 262056  78%    0.09K   8351       40     33404K buffer_head
151040 150537  99%    0.74K  30208        5    120832K ext3_inode_cache

为什么显示可回收的,但是又处于ACTIVE状态呢?求Linux内核达人看到后热心解释下:(

会不会由于是ACTIVE状态,导致dcache没有被自动回收释放掉呢?

让系统自动回收dcache

上一小节,我们已经提到,服务器上大部分的slab内存是SReclaimable可回收状态的,那么,我们能不能交给操作系统让他在某个时机自动触发回收操作呢?答案是肯定的。

查了一些关于Linux dcache的相关资料,发现操作系统会在到了内存临界阈值后,触发kswapd内核进程工作才进行释放,这个阈值的计算方法如下:

1. 首先,grep low /proc/zoneinfo,得到如下结果:

        low      1
        low      380
        low      12067

2. 将以上3列加起来,乘以4KB,就是这个阈值,通过这个方法计算后发现当前服务器的回收阈值只有48MB,因此很难看到这一现象,实际中可能等不到回收,操作系统就会hang住没响应了。

3. 可以通过以下方法调大这个阈值:将vm.extra_free_kbytes设置为vm.min_free_kbytes和一样大,则/proc/zoneinfo中对应的low阈值就会增大一倍,同时high阈值也会随之增长,以此类推。

$ sudo sysctl -a | grep free_kbytes       
vm.min_free_kbytes = 39847
vm.extra_free_kbytes = 0
$ sudo sysctl -w vm.extra_free_kbytes=836787 ######1GB ####系统中 没有vm.extra_free_kbytes 这个参数,修改下面的参数 $ /sbin/sysctl -w vm.min_free_kbytes=836787

4. 举个例子,当low阈值被设置为1GB的时候,当系统free的内存小于1GB时,观察到kswapd进程开始工作(进程状态从Sleeping变为Running),同时dcache开始被系统回收,直到系统free的内存介于low阈值和high阈值之间,停止回收。

原文链接:http://www.cnblogs.com/panfeng412/p/drop-caches-under-linux-system.html

http://www.cnblogs.com/panfeng412/p/drop-caches-under-linux-system-2.html

----------------------------------

 

http://os.51cto.com/art/201402/430458.htm

http://www.yidianzixun.com/article/news_e7e6ffd66c01fff1687c17dd3af9ce86?s=3

内存模块泄露排查

http://blog.csdn.net/cjf_iceking/article/details/19191595

 

http://leejia.blog.51cto.com/4356849/1431756

 

http://blog.csdn.net/vanbreaker/article/details/7671618

http://www.oenhan.com/size-512-slab-kmalloc

http://blog.chinaunix.net/uid-9543173-id-3571436.html

 

http://blog.csdn.net/bullbat/article/details/7194794

 

  • 大小: 6.3 KB
分享到:
评论

相关推荐

    Linux_slab_分配器剖析.pdf

    为了解决传统内存管理方法中的问题,特别是内存碎片问题,Linux 内核采用了 slab 分配器。这种内存管理机制的核心思想是在内存分配时保留对象的初始化状态,从而避免了每次分配新对象时都要重新初始化的问题。这样...

    Linux系统问题排查

    ### Linux系统问题排查知识点 #### 一、概述 在Linux系统运维过程中,系统问题排查是一项基本而重要的工作。本文档将详细介绍Linux系统中常见的问题排查方法,包括CPU问题、内存问题、网络问题以及磁盘问题等。...

    BIG-IP系统Linux主机部分内存问题故障排除方法

    例如,`inet_peer_cache`可能占用近2.2GB的slab cache,这可能会对系统性能造成影响。 #### 四、总结 在面对BIG-IP系统Linux主机部分的内存问题时,需要综合使用多种工具和技术手段进行诊断与排查。通过`free`、`...

    slaballocators.pdf

    ### Slab 分配器在 Linux 内核中的角色与实现 #### 一、概述 Slab 分配器作为 Linux 内核中一个重要的内存管理组件,主要负责为内核分配和管理固定大小的小对象。其设计目标是提高性能并减少内存碎片。本文将基于...

    一种Linux内存管理机制.pdf

    为了解决这个问题,Linux引入了Slab分配器。Slab分配器预先将内存资源组织成缓存(cache),并根据固定大小的对象进行管理。当需要内存时,可以直接从缓存中获取,不需要时则归还到缓存,减少了分配和释放的开销。...

    linux内核知识系列:内存管理

    Linux将物理内存划分为不同的区域,如DMA区(直接内存访问)、正常区、高内存区等,以便于管理和优化不同类型的内存需求。每个区域都有其特定的用途,例如DMA区主要为硬件设备提供高速访问的内存。 2. **页(Pages...

    linux内核缓冲区管理

    通过对Linux内核中的缓冲区管理机制的深入探讨,我们可以看出,Slab分配算法是Linux内核中处理对象缓存的一种高效方式。它不仅提高了内存使用的效率,还减少了系统的总体负载。随着技术的发展,未来Linux内核可能会...

    集群好书《高性能Linux服务器构建实战》 试读章节下载

    由国内著名技术社区联合推荐的2012年IT技术力作:《高性能Linux服务器构建实战:运维监控、性能调优与集群应用》,即将上架发行,此书从Web应用、数据备份与恢复、网络存储应用、运维监控与性能优化、集群高级应用等...

    Linux kernel developement

    对于开发者而言,理解并参与到Linux内核的开发是一项高技能挑战,也是深入理解操作系统原理的重要途径。 1. **Linux内核模块**:Linux内核模块(Kernel Module)是内核功能的可加载部分,可以在需要时动态插入到...

    Linux性能调优指南,IBM专家资深指导

    1. **Linux性能监控**:了解如何使用系统工具如top、vmstat、iostat、sar等,监控CPU使用率、内存占用、磁盘I/O和网络性能,以便发现潜在的性能瓶颈。 2. **内核参数调整**:讲解了如何通过调整内核参数(如sysctl...

    Linux内核2.4版源代码分析大全.rar

    1. 进程管理:在2.4版中,Linux内核引入了更先进的调度算法,如O(1)调度器,它能够在常数时间内完成调度,提高了高负载情况下的性能。此外,内核还支持实时进程,为需要低延迟的应用提供了更好的支持。 2. 虚拟内存...

    linux内核源码图解资料

    Linux内核是操作系统的核心部分,负责管理系统的硬件资源,提供基础服务给其他软件,并执行调度、内存管理、设备驱动程序等关键任务。这份"Linux内核图解资料"旨在通过图形化的方式帮助开发者和学习者更好地理解这个...

    Linux内核中动态内存检测机制的研究1

    随着Linux系统的广泛应用,特别是在服务器领域,对内存管理的效率和稳定性要求越来越高。动态内存检测机制就是确保内存在使用过程中不出错的关键技术之一。 动态内存检测机制的主要目标是预防和发现内存泄漏、内存...

    Linux面试专题及答案.pdf

    Linux操作系统在当代IT行业中占据着极其重要的地位,特别是在服务器端的操作系统市场中,Linux因其开源、稳定性高、安全性好等优点而广受欢迎。为了帮助对Linux感兴趣的开发者或系统管理员提高面试技巧,本文将详细...

    Linux内存管理大图

    最后,**内存泄漏**是Linux内存管理中需要防范的问题。如果程序忘记释放不再使用的内存,这部分内存就会永久占用,可能导致系统资源耗尽。因此,理解和使用适当的工具(如` Valgrind`)进行内存泄漏检测是必要的。 ...

    《深入理解LINUX内存管理》学习笔记

    Linux通过伙伴系统和 slab 分配器来减轻碎片问题。 8. **内存对齐**:为了优化访问速度和硬件兼容性,Linux内存管理系统会确保数据在特定边界对齐,比如CPU缓存行的大小。 9. **内存保护**:通过页表项的权限位,...

    linux内核注释,真正的深入并精通linux!

    内核还实现了内存分配器(如slab和伙伴系统),用于高效地分配和回收内存块。理解内存管理机制有助于优化程序的内存占用和避免内存泄漏。 2. **进程调度**:Linux内核使用抢占式调度策略,支持多种调度类,如CFS...

    Linux虚拟内存管理

    4. **内存分配器**:Linux的内存分配器,如SLAB和CMA(Contiguous Memory Allocator),负责高效地分配和回收内存块。它们旨在减少内存碎片并优化内存的使用,确保各种大小的对象都能快速地得到内存。 5. **缓存...

    Linux内存管理详解学习教案.pptx

    Linux通过伙伴系统(Buddy Algorithm)和SLAB/SLUB/SLOB分配器来减少这两种碎片。伙伴系统将内存块按大小分成对,以便更有效地分配和合并,而SLAB系列分配器则优化了小块内存的分配,减少了内部碎片。 Linux内存...

    Linux面试题,史上最全最经典

    在Linux中,申请大块内存特别是在系统启动阶段,可以使用`alloc_bootmem`函数来分配“启动内存”,这是一段不受页分配器和slab分配器管理的内存,因此在系统运行过程中不容易被其他内核组件占用。然而,这种方法的...

Global site tag (gtag.js) - Google Analytics