Linux 查看進程消耗內存狀況總結

 

在Linux中,有不少命令或工具查看內存使用狀況,今天咱們來看看如何查看進程消耗、佔用的內存狀況,Linux的內存管理和相關概念要比Windows複雜一些。在此以前,咱們須要瞭解一下Linux系統下面有關內存的專用名詞和專業術語概念:html

 

 

物理內存和虛擬內存java

 

物理內存:就是系統硬件提供的內存大小,是真正的內存,通常叫作內存條。也叫隨機存取存儲器(random access memory,RAM)又稱做隨機存儲器,是與CPU直接交換數據的內部存儲器,也叫主存(內存)。python

 

虛擬內存:相對於物理內存,在Linux下還有一個虛擬內存的概念,虛擬內存就是爲了知足物理內存的不足而提出的策略,它是利用磁盤空間虛擬出的一塊邏輯內存,用做虛擬內存的磁盤空間被稱爲交換空間(Swap Space)。Linux會在物理內存不足時,使用虛擬內存,內核會把暫時不用的內存塊信息寫到虛擬內存,這樣物理內存就獲得了釋放,這塊兒內存就能夠用於其餘目的,而須要用到這些內容的時候,這些信息就會被從新從虛擬內存讀入物理內存。git

 

 

Linuxbufferscachedgithub

 

在Linux中常常發現空閒的內存不多,彷佛全部的內存都被消耗殆盡了,表面上看是內存不夠用了,不少新手看到內存被消耗殆盡很是緊張,其實這個是由於Linux系統將空閒的內存用來作磁盤文件數據的緩存。這個致使你的系統看起來處於內存很是緊急的情況。可是實際上不是這樣。這個區別於Windows的內存管理。Linux會利用空閒的內存來作cached & buffers。緩存

 

 

buffers是指用來給塊設備作的緩衝大小(塊設備的讀寫緩衝區),它只記錄文件系統的metadata以及 tracking in-flight pages.tomcat

 

Buffers are associated with a specific block device, and cover caching of filesystem metadata as well as tracking in-flight pages. The cache only contains parked file data. That is, the buffers remember what's in directories, what file permissions are, and keep track of what memory is being written from or read to for a particular block device. The cache only contains the contents of the files themselves.oracle

 

  

cached是做爲page cache的內存, 文件系統的cache。你讀寫文件的時候,Linux內核爲了提升讀寫性能與速度,會將文件在內存中進行緩存,這部份內存就是Cache Memory(緩存內存)。即便你的程序運行結束後,Cache Memory也不會自動釋放。這就會致使你在Linux系統中程序頻繁讀寫文件後,你會發現可用物理內存會不多。其實這緩存內存(Cache Memory)在你須要使用內存的時候會自動釋放,因此你沒必要擔憂沒有內存可用app

 

Cached is the size of the page cache. Buffers is the size of in-memory block I/O buffers. Cached matters; Buffers is largely irrelevant.less

 

Cached is the size of the Linux page cache, minus the memory in the swap cache, which is represented by SwapCached (thus the total page cache size is Cached + SwapCached). Linux performs all file I/O through the page cache. Writes are implemented as simply marking as dirty the corresponding pages in the page cache; the flusher threads then periodically write back to disk any dirty pages. Reads are implemented by returning the data from the page cache; if the data is not yet in the cache, it is first populated. On a modern Linux system, Cached can easily be several gigabytes. It will shrink only in response to memory pressure. The system will purge the page cache along with swapping data out to disk to make available more memory as needed.

Buffers are in-memory block I/O buffers. They are relatively short-lived. Prior to Linux kernel version 2.4, Linux had separate page and buffer caches. Since 2.4, the page and buffer cache are unified and Buffers is raw disk blocks not represented in the page cache—i.e., not file data. The Buffers metric is thus of minimal importance. On most systems, Buffers is often only tens of megabytes.

 

 

Linux共享內存

 

共享內存是進程間通訊中最簡單的方式之一。共享內存容許兩個或更多進程訪問同一塊內存,就如同 malloc() 函數向不一樣進程返回了指向同一個物理內存區域的指針。當一個進程改變了這塊地址中的內容的時候,其它進程都會察覺到這個。其實所謂共享內存,就是多個進程間共同地使用同一段物理內存空間,它是經過將同一段物理內存映射到不一樣進程的虛擬空間來實現的。因爲映射到不一樣進程的虛擬空間中,不一樣進程能夠直接使用,不須要像消息隊列那樣進行復制,因此共享內存的效率很高。共享內存能夠經過mmap()映射普通文件機制來實現,也能夠System V共享內存機制來實現,System V是經過映射特殊文件系統shm中的文件實現進程間的共享內存通訊,也就是說每一個共享內存區域對應特殊文件系統shm中的一個文件。

 

 

另外,咱們還必須瞭解RSS、PSS、USS等相關概念:

 

     VSS Virtual Set Size 虛擬耗用內存(包含共享庫佔用的內存)

      RSS Resident Set Size 實際使用物理內存(包含共享庫佔用的內存)

      PSS Proportional Set Size 實際使用的物理內存(比例分配共享庫佔用的內存)

      USS Unique Set Size 進程獨自佔用的物理內存(不包含共享庫佔用的內存)

 

RSS(Resident set size),使用top命令能夠查詢到,是最經常使用的內存指標,表示進程佔用的物理內存大小。可是,將各進程的RSS值相加,一般會超出整個系統的內存消耗,這是由於RSS中包含了各進程間共享的內存。

 

PSS(Proportional set size)全部使用某共享庫的程序均分該共享庫佔用的內存時,每一個進程佔用的內存。顯然全部進程的PSS之和就是系統的內存使用量。它會更準確一些,它將共享內存的大小進行平均後,再分攤到各進程上去。

 

USS(Unique set size )進程獨自佔用的內存,它是PSS中本身的部分,它只計算了進程獨自佔用的內存大小,不包含任何共享的部分。

     

          

因此下面介紹的命令,有些查看進程的虛擬內存使用,有些是查看進程的RSS或實際物理內存。在講述的時候,咱們會標註這些信息。

 

 

 

top命令查看

 

執行top命令後,執行SHIFT +F ,能夠選擇按某列排序,例如選擇n後,就會按字段%MEM排序

 

clip_image001

 

 

固然也可使用shift+m 或大寫鍵M 讓top命令按字段%MEM來排序,固然你也能夠按VIRT(虛擬內存)、SWAP(進程使用的SWAP空間)、RES(實際使用物理內存,固然這裏因爲涉及共享內存緣故,你看到的實際內存很是大)

 

 

%MEM -- Memory usage (RES)

 

     A task's currently used share of available physical memory

     

VIRT -- virtual memory 

   

    The  total  amount  of virtual memory used by the task.  It includes all code, data and shared libraries plus pages that have been swapped out. (Note: you can define the STATSIZE=1 environment variable and the VIRT will be calculated from the /proc/#/state VmSize field.)

 

    VIRT = SWAP + RES

 

SWAP  --  Swapped size (kb)

 

   The swapped out portion of a tasks total virtual memory image.

 

RES  --  Resident size (kb)

       

    RES = CODE + DATA.

 

         

 

是否有人會以爲奇怪,爲何%MEM這一列的值加起來會大於100呢? 這個是由於這裏計算的時候包含了共享內存的緣故,另外因爲共享內存的緣故,你看到進程使用VIRT或RES都很是高。因爲大部分的物理內存一般在多個應用程序之間共享,名爲實際使用物理內存(RSS,對應top命令裏面的RES)的這個標準的內存耗用衡量指標會大大高估內存耗用狀況。

 

clip_image002

 

 

 

ps命令查看

 

 

 

使用ps命令找出佔用內存資源最多的20個進程(數量能夠任意設置)

 

 

# ps aux | head -1;ps aux |grep -v PID |sort -rn -k +4 | head -20
USER       PID %CPU %MEM    VSZ   RSS TTY      STAT START   TIME COMMAND
oracle   32147 11.0 51.2 13252080 12666320 ?   Rs   Aug24 163:16 ora_s000_SCM2
oracle   32149 14.2 50.9 13250344 12594264 ?   Ss   Aug24 210:41 ora_s001_SCM2
oracle   32153  4.2 49.6 13250820 12279432 ?   Ss   Aug24  62:27 ora_s003_SCM2
oracle   32155  2.5 48.6 13250268 12040732 ?   Ss   Aug24  38:21 ora_s004_SCM2
oracle   32157  1.2 44.5 13250296 11011708 ?   Ss   Aug24  18:31 ora_s005_SCM2
oracle   32151  2.7 39.7 13350436 9829944 ?    Ss   Aug24  41:18 ora_s002_SCM2
oracle   32159  0.5 38.9 13250704 9625764 ?    Ss   Aug24   8:18 ora_s006_SCM2
oracle   32161  0.2 26.3 13250668 6507244 ?    Ss   Aug24   3:38 ora_s007_SCM2
oracle   32129  0.0 25.5 13299084 6324644 ?    Ss   Aug24   1:25 ora_dbw0_SCM2
oracle   32181  0.0 15.8 13250152 3913260 ?    Ss   Aug24   0:56 ora_s017_SCM2
oracle   32145  2.7 15.3 13255256 3786456 ?    Ss   Aug24  40:11 ora_d000_SCM2
oracle   32127  0.0 15.2 13248996 3762860 ?    Ss   Aug24   0:05 ora_mman_SCM2
oracle   32163  0.0 14.2 13250108 3525160 ?    Ss   Aug24   1:04 ora_s008_SCM2
oracle   32165  0.0  8.1 13250172 2007704 ?    Ss   Aug24   0:37 ora_s009_SCM2
oracle   32169  0.0  6.6 13250060 1656864 ?    Ss   Aug24   0:08 ora_s011_SCM2
oracle   32177  0.0  6.0 13250148 1498760 ?    Ss   Aug24   0:12 ora_s015_SCM2
oracle   32187  0.0  5.1 13250084 1267384 ?    Ss   Aug24   0:06 ora_s020_SCM2
oracle   32179  0.0  5.1 13250584 1280156 ?    Ss   Aug24   0:05 ora_s016_SCM2
oracle   32167  0.0  5.0 13250060 1248668 ?    Ss   Aug24   0:08 ora_s010_SCM2
oracle   32175  0.0  3.4 13250596 857380 ?     Ss   Aug24   0:03 ora_s014_SCM2

 

 

#ps -eo pmem,pcpu,rss,vsize,args | sort -k 1 -n -r | less

 

查看進程佔用的實際物理內存(與smem看到實際物理內存大小有出入,這裏解釋一下:SIZE: 進程使用的地址空間, 若是進程映射了100M的內存, 進程的地址空間將報告爲100M內存. 事實上, 這個大小不是一個程序實際使用的內存數. 因此這裏看到的內存跟smem看到的大小有出入)

 

ps -eo size,pid,user,command --sort -size | awk '{ hr=$1/1024 ; printf("%13.2f Mb ",hr) } { for ( x=4 ; x<=NF ; x++ ) { printf("%s ",$x) } print "" }' |cut -d "" -f2 | cut -d "-" -f1

 

clip_image003

 

 

ps aux  | awk '{print $6/1024 " MB\t\t" $11}'  | sort -n

 

 

 

 

smem命令查看

 

 

關於smem命令,這裏不作介紹,直接參考連接Linux監控工具介紹系列——smem

 

 

#smem -rs pss

 

clip_image004

 

 

 

 

pmap命令查看

 

 

# ps -ef | grep tomcat

# pmap 32341

 

clip_image005

 

# pmap -x  32341

 

The -x option can be used to provide information about the memory allocation and mapping types per mapping. The amount of resident, non-shared anonymous, and locked memory is shown for each mapping

 

clip_image006

 

 

 

 

python腳本查看

 

 

網上有個python腳本計算程序或進程的內存使用狀況,地址位於https://raw.githubusercontent.com/pixelb/ps_mem/master/ps_mem.py

 

python ps_mem.py

 

clip_image007

 

 

[root@mylnx03 ~]# python ps_mem.py -h
Usage: ps_mem [OPTION]...
Show program core memory usage
 
  -h, -help                   Show this help
  -p <pid>[,pid2,...pidN]     Only show memory usage PIDs in the specified list
  -s, --split-args            Show and separate by, all command line arguments
  -t, --total                 Show only the total value
  -d, --discriminate-by-pid   Show by process rather than by program
  -S, --swap                  Show swap information
  -w <N>                      Measure and show process memory every N seconds
[root@mylnx03 ~]# python ps_mem.py  -p 32341
Private  +   Shared  =  RAM used       Program
 
411.2 MiB + 184.0 KiB = 411.4 MiB       java
---------------------------------
                        411.4 MiB
=================================

 

參考資料:

 

 

https://stackoverflow.com/questions/131303/how-to-measure-actual-memory-usage-of-an-application-or-process

http://www.cnblogs.com/kerrycode/p/5079319.html

https://raw.githubusercontent.com/pixelb/ps_mem/master/ps_mem.py

相關文章
相關標籤/搜索