在Linux中,如何判断正在使用多少内存进程?

时间:2010-10-04 08:27:56

标签: linux unix memory-leaks memory-management

我想我的LAMP应用程序可能有内存泄漏(内存耗尽,交换开始被使用等)。如果我能看到各种进程使用了​​多少内存,它可能有助于我解决我的问题。我有办法在* nix中看到这些信息吗?

13 个答案:

答案 0 :(得分:89)

获得正确的内存使用比人们想象的要复杂。我could find is的最佳方式:

echo 0 $(awk '/TYPE/ {print "+", $2}' /proc/`pidof PROCESS`/smaps) | bc

其中“PROCESS”是您要检查的流程的名称,“TYPE”是以下之一:

  • Rss :驻留内存使用情况,进程使用的所有内存,包括此进程与其他进程共享的所有内存。它不包括swap;
  • Shared :此进程与其他进程共享的内存;
  • Private :此进程使用的私有内存,您可以在这里查找内存泄漏;
  • Swap :交换进程使用的内存;
  • Pss :比例集大小,一个很好的整体记忆指标。调整共享的Rss:如果一个进程具有1MiB私有和20MiB在其他10个进程之间共享,则Pss为1 + 20/10 = 3MiB

其他有效值为 Size (即虚拟大小,几乎毫无意义)和 Referenced (当前标记为的内存量)引用或访问)。

您可以使用watch或其他一些bash-script-fu来关注您要监控的进程的值。

有关smaps的更多信息:http://www.kernel.org/doc/Documentation/filesystems/proc.txt

答案 1 :(得分:44)

我不知道为什么答案看起来如此复杂......使用ps执行此操作似乎很简单:

mem()
{                                                                                                      
    ps -eo rss,pid,euser,args:100 --sort %mem | grep -v grep | grep -i $@ | awk '{printf $1/1024 "MB"; $1=""; print }'
}

使用示例:

$ mem mysql
0.511719MB 781 root /bin/sh /usr/bin/mysqld_safe
0.511719MB 1124 root logger -t mysqld -p daemon.error
2.53516MB 1123 mysql /usr/sbin/mysqld --basedir=/usr --datadir=/var/lib/mysql --plugin-dir=/usr/lib/mysql/plugin --user=mysql --pid-file=/var/run/mysqld/mysqld.pid --socket=/var/run/mysqld/mysqld.sock --port=3306

答案 2 :(得分:34)

使用ps查找应用程序的进程ID,然后使用top -p1010(将1010替换为实际进程ID)。  RES列是使用的物理内存,VIRT列是使用的虚拟内存 - 包括库和交换内存。

使用“man top”

可以找到更多信息

答案 3 :(得分:15)

首先得到pid:

ps ax | grep [process name]

然后:

top -p PID

您可以同时观看各种流程:

top -p PID1 -p PID2 

答案 4 :(得分:13)

您可以使用pmap报告内存使用情况。

梗概:

pmap [ -x | -d ] [ -q ] pids... 

答案 5 :(得分:7)

更优雅的方法:

echo "Memory usage for PID <>:"; for mem in {Private,Rss,Shared,Swap,Pss};do grep $mem /proc/<pid>/smaps | awk -v mem_type="$mem" '{i=i+$2} END {print mem_type,"memory usage:"i}' ;done

答案 6 :(得分:6)

感谢。我用它来创建这个简单的bash脚本,可用于监视进程及其内存使用情况:

$ watch watchmypid.sh

#!/bin/bash
#

PROCESSNAME=changethistoyourprocessname
MYPID=`pidof $PROCESSNAME`

echo "=======";
echo PID:$MYPID
echo "--------"
Rss=`echo 0 $(cat /proc/$MYPID/smaps  | grep Rss | awk '{print $2}' | sed 's#^#+#') | bc;`
Shared=`echo 0 $(cat /proc/$MYPID/smaps  | grep Shared | awk '{print $2}' | sed 's#^#+#') | bc;`
Private=`echo 0 $(cat /proc/$MYPID/smaps  | grep Private | awk '{print $2}' | sed 's#^#+#') | bc;`
Swap=`echo 0 $(cat /proc/$MYPID/smaps  | grep Swap | awk '{print $2}' | sed 's#^#+#') | bc;`
Pss=`echo 0 $(cat /proc/$MYPID/smaps  | grep Pss | awk '{print $2}' | sed 's#^#+#') | bc;`

Mem=`echo "$Rss + $Shared + $Private + $Swap + $Pss"|bc -l`

echo "Rss     " $Rss
echo "Shared  " $Shared
echo "Private " $Private
echo "Swap    " $Swap
echo "Pss     " $Pss
echo "=================";
echo "Mem     " $Mem
echo "=================";

答案 7 :(得分:4)

使用tophtop并注意“RES”(常驻内存大小)列。

答案 8 :(得分:4)

你想要的工具是ps。 要获取有关java程序正在执行的操作的信息:

ps -F -C java 

获取有关http的信息:

ps -F -C httpd

如果您的计划在您有机会运行之前结束,请打开另一个终端并运行:

while true; do ps -F -C myCoolCode ; sleep 0.5s ; done

答案 9 :(得分:4)

您可以使用pmap + awk

我们最有可能感兴趣的是RSS内存,它是下面(82564)示例pmap输出的最后一行的第3列。

$ pmap -x <pid>

Address           Kbytes     RSS   Dirty Mode   Mapping

....

00007f9caf3e7000       4       4       4 r----  ld-2.17.so
00007f9caf3e8000       8       8       8 rw---  ld-2.17.so
00007fffe8931000     132      12      12 rw---    [ stack ]
00007fffe89fe000       8       8       0 r-x--    [ anon ]
ffffffffff600000       4       0       0 r-x--    [ anon ]
----------------  ------  ------  ------
total kB          688584   82564    9592

然后使用Awk提取该值。

$ pmap -x <pid> | awk '/total/ { print $4 "K" }'

pmap值以千字节为单位。如果我们想要它以兆字节为单位,我们可以做这样的事情。

$ pmap -x <pid> | awk '/total/ { print $4 / 1024 "M" }'

答案 10 :(得分:4)

如果您没有要跟踪的当前或长时间运行流程,可以使用/usr/bin/time

这与Bash time不同(正如您将看到的)。

例如

# /usr/bin/time -f "%M" echo

2028

这是&#34;进程在其生命周期内的最大驻留集大小,以千字节为单位&#34; (引自手册页)。也就是说,与top等人中的RES相同。

您可以从/usr/bin/time获得更多。

# /usr/bin/time -v echo

Command being timed: "echo"
User time (seconds): 0.00
System time (seconds): 0.00
Percent of CPU this job got: 0%
Elapsed (wall clock) time (h:mm:ss or m:ss): 0:00.00
Average shared text size (kbytes): 0
Average unshared data size (kbytes): 0
Average stack size (kbytes): 0
Average total size (kbytes): 0
Maximum resident set size (kbytes): 1988
Average resident set size (kbytes): 0
Major (requiring I/O) page faults: 0
Minor (reclaiming a frame) page faults: 77
Voluntary context switches: 1
Involuntary context switches: 0
Swaps: 0
File system inputs: 0
File system outputs: 0
Socket messages sent: 0
Socket messages received: 0
Signals delivered: 0
Page size (bytes): 4096
Exit status: 0

答案 11 :(得分:2)

为什么所有这些复杂的答案都有各种shell脚本? 使用htop,它会自动更改大小,您可以选择要显示的信息,它可以在终端中使用,因此不需要桌面。 示例:htop -d8

答案 12 :(得分:1)

使用

  • ps u`pidof $ TASKS_LIST` ps u -C $ TASK
  • ps xu --sort%mem
  • ps h -o pmem -C $ TASK

示例:

ps-of()
{
 ps u `pidof "$@"`
}

$ ps-of firefox
USER       PID %CPU %MEM    VSZ   RSS TTY      STAT START   TIME COMMAND
const    18464  5.9  9.4 1190224 372496 ?      Sl   11:28   0:33 /usr/lib/firefox/firefox

$ alias ps-mem="ps xu --sort %mem | sed -e :a -e '1p;\$q;N;6,\$D;ba'"
$ ps-mem 
USER       PID %CPU %MEM    VSZ   RSS TTY      STAT START   TIME COMMAND
const     3656  0.0  0.4 565728 18648 ?        Sl   Nov21   0:56 /usr/bin/python /usr/lib/ubuntuone-client/ubuntuone-syncdaemon
const    11361  0.3  0.5 1054156 20372 ?       Sl   Nov25  43:50 /usr/bin/python /usr/bin/ubuntuone-control-panel-qt
const     3402  0.0  0.5 1415848 23328 ?       Sl   Nov21   1:16 nautilus -n
const     3577  2.3  2.0 1534020 79844 ?       Sl   Nov21 410:02 konsole
const    18464  6.6 12.7 1317832 501580 ?      Sl   11:28   1:34 /usr/lib/firefox/firefox

$ ps h -o pmem -C firefox
12.7