[转帖]Hp unix下单进程内存的使用问题_VMware, Unix及操作系统讨论区_Weblogic技术|Tuxedo技术|中间件技术|Oracle论坛|JAVA论坛|Linux/Unix技术|hadoop论坛_联动北方技术论坛  
网站首页 | 关于我们 | 服务中心 | 经验交流 | 公司荣誉 | 成功案例 | 合作伙伴 | 联系我们 |
联动北方-国内领先的云技术服务提供商
»  游客             当前位置:  论坛首页 »  自由讨论区 »  VMware, Unix及操作系统讨论区 »
总帖数
1
每页帖数
101/1页1
返回列表
0
发起投票  发起投票 发新帖子
查看: 4844 | 回复: 0   主题: [转帖]Hp unix下单进程内存的使用问题        下一篇 
    本主题由 Administrator 于 2019-3-2 20:59:35 移动
yang.liu
注册用户
等级:少校
经验:1182
发帖:77
精华:1
注册:2014-1-3
状态:离线
发送短消息息给yang.liu 加好友    发送短消息息给yang.liu 发消息
发表于: IP:您无权察看 2014-1-8 15:12:43 | [全部帖] [楼主帖] 楼主

摘要:有时会看到hp-unix下单个Oracle进程占用内存很多,有时又会很少,好多人对此都有些疑惑,是正常的还是内存泄露?同时好多人对相关的概念也不清晰,本文以一个问题入门来解答一下这方面的疑问。

1 引言
一直未太关注过Hp unix下单进程内存的使用问题,因我的各正式系统库的这部分都是很正常的,每个Oracle的进程内存的占用以性能观测工具观察在7mb左右。且系统的内存使用比也比较平稳。直到最近,itpub赵宇的一个问题才使我对Hp unix下Oracle进程的内存使用捉摸一番。帖子中单个Oracle进程以kmeminfo工具及Top工具来看占用内存很多个在100mb之上。新开一个Oracle连接什么也不做相应的后台进程也会占用93.2mb内存。相应的问题就来了,难道发生了内存泄露?单个进程占这么多内存正常吗?93.2mb内存由哪些部分组成的呢?

2 本文使用的系统工具
2.1 glance软件
Glance是Hp出品的一个非常好用的hp unix的性能监测和诊断工具,功能类似Aix的nmon工具。可以用其十分方便的表现系统性能(cpu、内存、IO、网络。。)的时时态及保存状态的历史,方便的找出系统性能的瓶颈,glance是一个比Top好用的十分多的一个工具。不过glance不是像Top一样的免费软件,glance工具需要购买,也可以向Hp工程师要一个免注册码的glance。Hp unix application盘上有一个Trail版的glance,可以使用30天,可以临时用或感受一下。这个工具可以方便的诊断单进程的内存使用,包含了类以solaris中的pmap命令的功能。

sd11#[root:/]swlist -l product|grep -i glance
Glance C.03.72.00 HP GlancePlus/UX


2.2 kmeminfo工具
Kmeminfo是一个hp的unsupport的内部工具,非常好用,用于内存具体使用的诊断。例如我想知道系统中所有的用户进程每个占用了多少内存?内存占用系统部分每个子部分都用��多少?Buffer cache占用的细节等等。Kmeminfo –user查看每个用户进程每个占用了多少内存的结果是按降序排序的,看起来非常的方便。如需要可以向Hp工程师要一个。

2.3 procsize 工具
Procsize也是一个unsupport的内部工具,用于观察进程的UAREA、TEXT、DATA、STACK等部分都为多少的细节,只所以使用这个工具是为了更好的说明ps命令的SZ。
2.4 ps命令
不用太细说,应该是每个人都用过,查看进程状态的。

3 问题重现
3.1 测试的环境
测试的环境是我的一个应用的测试系统,glance观察发现很多的Oracle进程占用了60mb多的内存。系统具体配置如下:
系统:3cpu,6GB物理内存,hp-ux11.11的操作系统,做过patch分析无问题。
数据库:Oracle 9.2.0.6 2GB内存用于SGA区

3.2 测试流程细节
○1打开glance初步看一下第一页,很多oracle进程占内存(RSS)都在60mb之上

Process Name PID PPID Pri Name ( 300% max) CPU IO Rate RSS Cnt
--------------------------------------------------------------------------------
glance 7961 11741 154 root 0.9/ 1.8 0.5 0.0/ 0.0 21.4mb 1
oraclevcard 2194 1 154 oracle 0.7/ 0.1 3060.2 0.0/ 0.0 61.4mb 1
midaemon 15077 1 -16 root 0.2/ 0.2 6648.9 0.0/ 0.0 26.2mb 3
oraclevcard 2204 1 154 oracle 0.0/ 0.1 3062.9 0.0/ 0.0 61.1mb 1
oraclevcard 14589 1 154 oracle 0.0/ 0.0 1.0 0.0/ 0.0 80.5mb 1
oraclevcard 25202 1 154 oracle 0.0/ 0.0 17.8 0.0/ 0.0 61.2mb 1
oraclevcard 25149 1 154 oracle 0.0/ 0.0 27.6 0.0/ 0.0 79.9mb 1
oraclevcard 17069 1 154 oracle 0.0/ 0.0 23.0 0.0/ 0.0 79.6mb 1
scopeux 15078 1 127 root 0.0/ 0.1 3753.4 0.0/ 0.1 23.5mb 1
oraclevcard 2206 1 154 oracle 0.0/ 0.1 3060.9 0.0/ 0.0 61.4mb 1
oraclevcard 2214 1 154 oracle 0.0/ 0.0 410.9 0.0/ 0.0 64.7mb 1
oraclevcard 2208 1 154 oracle 0.0/ 0.1 3064.9 0.0/ 0.0 61.1mb 1
oraclevcard 16060 1 154 oracle 0.0/ 0.0 39.8 0.0/ 0.0 79.5mb 1
oraclevcard 10987 1 154 oracle 0.0/ 0.0 104.3 0.0/ 0.0 79.4mb 1
oraclevcard 11009 1 154 oracle 0.0/ 0.2 695.2 0.0/ 0.0 80.0mb 1
oraclevcard 7900 1 154 oracle 0.0/ 0.2 0.2 0.0/ 0.0 60.7mb 1
oraclevcard 7861 7860 154 oracle 0.0/ 0.1 0.1 0.0/ 0.0 62.1mb 1
oraclevcard 6838 1 154 oracle 0.0/ 0.0 0.2 0.0/ 0.0 64.4mb 1
oraclevcard 6882 1 154 oracle 0.0/ 0.0 0.3 0.0/ 0.0 62.2mb 1
oraclevcard 6890 1 154 oracle 0.0/ 0.0 0.2 0.0/ 0.0 63.9mb 1
oraclevcard 6015 1 154 oracle 0.0/ 0.0 0.2 0.0/ 0.0 60.7mb 1
oraclevcard 5675 1 154 oracle 0.0/ 0.0 0.5 0.0/ 0.0 64.0mb 1
oraclevcard 5705 1 154 oracle 0.0/ 0.0 0.2 0.0/ 0.0 60.9mb 1
oraclevcard 5815 1 154 oracle 0.0/ 0.0 0.3 0.0/ 0.0 60.7mb 1
oraclevcard 6374 1 154 oracle 0.0/ 0.0 1.3 0.0/ 0.0 79.5mb 1
oraclevcard 2202 1 154 oracle 0.0/ 0.1 3061.3 0.0/ 0.0 61.4mb 1
oraclevcard 2200 1 154 oracle 0.0/ 0.1 3059.1 0.0/ 0.0 61.4mb 1


○2 开一个Oracle连接并找到其进程号为7861

$ sqlplus qiuyb/test
SQL*Plus: Release 9.2.0.6.0 - Production on Fri Apr 18 09:12:06 2008
Copyright (c) 1982, 2002, Oracle Corporation. All rights reserved.
Connected to:
Oracle9i Enterprise Edition Release 9.2.0.6.0 - 64bit Production
With the Partitioning, OLAP and Oracle Data Mining options
JServer Release 9.2.0.6.0 - Production
SQL>
# ps -ef|grep "sqlplus qiuyb"
oracle 7860 7579 0 09:13:04 pts/te 0:00 sqlplus qiuyb/byuiq_145
root 7891 11741 1 09:13:35 pts/td 0:00 grep sqlplus qiuyb
#
# ps -ef|grep 7860
oracle 7860 7579 0 09:13:04 pts/te 0:00 sqlplus qiuyb/test
oracle 7861 7860 0 09:13:04 ? 0:00 oraclevcard (DESCRIPTION=(LOCAL=YES)(ADDRESS=(PROTOCOL=beq)))
root 8107 11741 1 09:16:24 pts/td 0:00 grep 7860


○3glance里7861进程占用内存(RSS)为57.9mb

User CPU Util Cum Disk Thd
Process Name PID PPID Pri Name ( 300% max) CPU IO Rate RSS Cnt
--------------------------------------------------------------------------------
oraclevcard 7861 7860 154 oracle 0.0/ 0.0 0.2 0.0/ 0.0 57.9mb 1


○4kmeminfo里7861占用内存为56.6mb

# ./kmeminfo -user |grep 7861
7861 7860 548101 2.1g 14481 56.6m 14332 56.0m oracle


○5 ps里7861占用了16992个内存页,计算起来为66.375mb
每个内存页为4096字节:

# getconf PAGE_SIZE
4096


执行ps命令:

# ps -flp 7861
F S UID PID PPID C PRI NI ADDR SZ WCHAN STIME TTY TIME COMD
1001 S oracle 7861 7860 0 154 20 6e5745c0 16992 4f54e32e 09:13:04 ? 0:00 oraclevcard (DESCRIPTION=(LOCAL=YES)(ADDRESS=(PROTOCOL=beq)))


计算一下:

16992*4096/1024/1024=66.375mb


○6 看一下Oracle库内查到的该进程的pga占用为多少,结果为306kb

SQL> SELECT pga_alloc_mem,pga_max_mem FROM v$process WHERE spid=7861
2 /
PGA_ALLOC_MEM PGA_MAX_MEM
------------- -----------
313689 313689


3.3 疑惑和问题
3.3.1 疑惑1
从3.2的测试中可以看到5861进程什么都未做,在glance中表现为占用57.9mb内存,kmeminfo表现为56.6mb内存,ps命令中为66.375 mb内存,哪个内存表现才为5861真实的物理内存占用?

3.3.2 疑惑2
Oracle库内5861使用pga才为300多kb,系统为什么分配给5861这么多的内存?出现了内存泄露?56.6mb的内存占用都含哪些部分?哪一部分占用的大呢?

4 解惑及我的见解
4.1 glance、kmeminfo及ps都不是进程真实占用物理内存的反映
4.1.1 glance与kmeminfo对进程的内存占用是一样,都为RSS
glance、kmeminfo及ps都不是进程真实占用内存的反映,这是我的第一个见解。这么一说可能会有N个人出来反对我,主要原因在于 kmeminfo这个工具。从kmeminfo这个工具的使用上看,它的体现的该是每个部分占用物理内存的大小,它的-user选项该也是每个进程实际占用物理内存,用过这个工具的人都会这样理解,我原来也这样认为。经过认真的评测,发现glance与kmeminfo对于某一个进程的内存占用实际上是一样的,也是一个东西,即为RSS,而不是真���的物理内存。这里又出现了一个概念上的问题,何为进程的真实的物理内存?何为RSS?

4.1.2 何为进程的真实的物理内存?何为RSS?
关于RSS,在hp-unix中的定义为:The size (in KB) of resident memory allocated for the process.
指的是进程相关数据驻留内存的大小。Hp-unix定义的RSS的计算公式为:

RSS = sum of private region pages +(sum of shared region pages /number of references)


其中sum of private region pages即为进程占用真实的物理内存(sum of shared region pages /number of references)表现的是为共享内存部分在某一个进程上的均分。

此时我们对一个进程内存占用该有一个清晰的理解,当fork一个进程,假定名字为p1,malloc一个区域,这个区域用于存放进程的data、 stack、code等这些私有的数据,这才是真实的其物理内存的占用。同时系统内会有一些共享内存部分(ipcs看到的),如oracle的SGA 区,p1也会引用到。此时p1的RSS该为:自已私有的占用+SGA它的引用。
假定p1的私有占用为2mb,它只引用共享部分如2gb的SGA区的5mb,那么p1的RSS=2+5=7mb,在glancee及kmeminfo的表现都会为7mb。

4.2 glance与kmeminfo的值不一样的原因在于glance的计算方式而产生的差别
4.1.1有人就会有不同意见,因为5861进程在glance中表现为占用57.9mb内存,kmeminfo表现为56.6mb内存,明明值不一样, 为什么说是一个东西?原因在于glance的不实时性及glance的计算方式而产生的差别。
做一个大量的抽样可以得到glance与kmeminfo的值不一样,可却相差很小,就像如上的57.9与56.6一样,也可以认为是等同的。 Glance默认是每2秒刷新一次的,而且由于unix内存的管理如page in/out,两者会有一点差别。同时看一下Hp对Rss的描述也会知道,这有glance的计算方式而产生的差别的因素,原文中的一段如下:

On HP-UX, the calculation of this metric differs depending on whether this process has used any CPU time since the midaemon process was started. This metric is less accurate and does not include shared memory regions in its calculation when the process has been idle since the midaemon was started.
This value is only updated when a process uses CPU. Thus, under memory pressure, this value may be higher than the actual amount of resident memory for processes which are idle because their memory pages may no longer be resident or the reference count for shared segments may have changed.


即因glance软件启用后,是否进程使用了cpu会差生RSS计算上的一点差别。

4.3 ps中的sz是text、data和stack三项的和,而text在hp-ux下属于共享部分, 故产生了ps的计算也不准确的状况
3.2的测试可以看到ps里7861的sz为16992个内存页,计算起来为66.375mb,那这16992个内存页由哪些部分组成的呢?每
每部分都为多少呢?man一个ps命令就能知道ps中的sz是text、datat和stack三项的和。如果想要知道text、data和stack都为多少需要借助procsize工具了。

# ./procsize -R -p 7861
libp4 (6.93): Opening /stand/vmunix /dev/kmem
Loading symbols from /stand/vmunix
regions set to 1000
hpux 11.11 64 bit in Wide mode
nproc=30000
pid Comm UAREA TEXT DATA STACK SHMEM IO MMAP Total
7861 oracle r 8 16384 512 96 524661 0 1203 542865


其中-R表明查驻留的部分,可见16384(TEXT)+512(DATA )+96(STACK)恰好为16992。因TEXT部分在在hp-ux下属于共享部分,故产生了ps的计算也不准确的状况。
4.4 glance诊断单进程使用过多的问题
4.4.1 查看内存详细map列表
做了如些多的铺垫,该进入正题了,如下解析一下7861进程glance中57.9mb RSS源于何处的问题。
关注一下7861进程,进程列表界面按"s"键,然后提供process id 7861。

User CPU Util Cum Disk Thd
Process Name PID PPID Pri Name ( 300% max) CPU IO Rate RSS Cnt
--------------------------------------------------------------------------------
oraclevcard 7861 7860 154 oracle 0.0/ 0.0 0.2 0.0/ 0.0 57.9mb 1
Resources PID: 7861, oraclevcard PPID: 7860 euid: 103 User: oracle
--------------------------------------------------------------------------------
CPU Usage (util): 0.0 Log Reads : 0 Wait Reason : PIPE
User/Nice/RT CPU: 0.0 Log Writes: 0 Total RSS/VSS : 57.9mb/ 58.9mb
System CPU : 0.0 Phy Reads : 0 Traps / Vfaults: 0/ 0
Interrupt CPU : 0.0 Phy Writes: 0 Faults Mem/Disk: 0/ 0
Cont Switch CPU : 0.0 FS Reads : 0 Deactivations : 0
Scheduler : HPUX FS Writes : 0 Forks & Vforks : 0
Priority : 154 VM Reads : 0 Signals Recd : 0
Nice Value : 20 VM Writes : 0 Mesg Sent/Recd : 0/ 0
Dispatches : 0 Sys Reads : 0 Other Log Rd/Wt: 0/ 0
Forced CSwitch : 0 Sys Writes: 0 Other Phy Rd/Wt: 0/ 0
VoluntaryCSwitch: 0 Raw Reads : 0 Proc Start Time
Running CPU : 0 Raw Writes: 0 Fri Apr 18 09:14:16 2008
CPU Switches : 0 Bytes Xfer: 0kb :
Argv1: (DESCRIPTION=(LOCAL=YES)
Cmd : oraclevcard (DESCRIPTION=(LOCAL=YES)(ADDRESS=(PROTOCOL=beq)))


再键入”M”,进入详细的内存分布列表,如下:

Memory Regions PID: 7861, oraclevcard PPID: 7860 euid: 103 User: oracle
Type RefCt RSS VSS Locked File Name
--------------------------------------------------------------------------------
NULLDR/Shared 137 4kb 4kb 0kb <nulldref>
MEMMAP/Shared 55 4kb 4kb 0kb /var/spool/pwgr/status
TEXT /Shared 41 64.0mb 64.0mb 0kb /oracle/.../bin/oracle
UAREA /Priv 1 32kb 32kb 0kb <uarea>
DATA /Priv 1 2.0mb 2.0mb 0kb /oracle/.../bin/oracle
MEMMAP/Priv 1 512kb 512kb 0kb <mmap>
MEMMAP/Priv 1 16kb 16kb 0kb <mmap>
MEMMAP/Priv 1 8kb 8kb 0kb <mmap>
MEMMAP/Priv 1 60kb 60kb 0kb /usr/lib/pa20_64/libc.2
MEMMAP/Priv 1 52kb 52kb 0kb <mmap>
MEMMAP/Priv 1 12kb 12kb 0kb /usr/lib/pa20_64/libm.2
MEMMAP/Priv 1 4kb 4kb 0kb /usr/lib/pa20_64/libdl.1
MEMMAP/Priv 1 8kb 8kb 0kb <mmap>
MEMMAP/Priv 1 4kb 4kb 0kb /usr/.../libnss_dns.1
MEMMAP/Priv 1 12kb 12kb 0kb /usr/.../libpthread.1
MEMMAP/Priv 1 8kb 8kb 0kb <mmap>
MEMMAP/Priv 1 4kb 4kb 0kb /usr/lib/pa20_64/librt.2
MEMMAP/Priv 1 36kb 272kb 0kb /usr/lib/pa20_64/libcl.2
MEMMAP/Priv 1 0kb 32kb 0kb <mmap>
MEMMAP/Priv 1 8kb 8kb 0kb <mmap>
MEMMAP/Priv 1 500kb 504kb 0kb /oracle/.../libjox9.sl
MEMMAP/Priv 1 0kb 12kb 0kb <mmap>
MEMMAP/Priv 1 4kb 4kb 0kb /oracle/.../libskgxn9.sl
MEMMAP/Priv 1 4kb 4kb 0kb /oracle/.../libodmd9.sl
MEMMAP/Priv 1 8kb 8kb 0kb <mmap>
MEMMAP/Priv 1 8kb 8kb 0kb /usr/lib/pa20_64/dld.sl
MEMMAP/Priv 1 4kb 4kb 0kb <mmap>
STACK /Priv 1 384kb 576kb 0kb <stack>
MEMMAP/Shared 44 140kb 140kb 0kb /usr/lib/pa20_64/dld.sl
MEMMAP/Shared 43 12kb 12kb 0kb /usr/.../libnss_dns.1
MEMMAP/Shared 44 16kb 20kb 0kb /usr/lib/pa20_64/librt.2
MEMMAP/Shared 41 4kb 4kb 0kb /oracle/.../libodmd9.sl
MEMMAP/Shared 41 8kb 8kb 0kb /oracle/.../libskgxn9.sl
MEMMAP/Shared 44 16kb 16kb 0kb /usr/lib/pa20_64/libdl.1
MEMMAP/Shared 44 72kb 532kb 0kb /usr/lib/pa20_64/libcl.2
MEMMAP/Shared 44 96kb 96kb 0kb /usr/.../libpthread.1
MEMMAP/Shared 44 136kb 152kb 0kb /usr/lib/pa20_64/libm.2
MEMMAP/Shared 44 1.1mb 1.1mb 0kb /usr/lib/pa20_64/libc.2
MEMMAP/Shared 41 1.9mb 5.4mb 0kb /oracle/.../libjox9.sl
SHMEM /Shared 41 2.00gb 2.02gb 0kb <shmem>
Text RSS/VSS: 64mb/ 64mb Data RSS/VSS:2.0mb/2.0mb Stack RSS/VSS:384kb/576kb
Shmem RSS/VSS:2.0gb/2.0gb Other RSS/VSS:4.7mb/9.0mb


4.4.2 信息项说明
RefCt指的是Reference Count,即有多少个进程引用共享区域
/Priv表明该内存区是进程私有的,此时RefCt也为1。/Shared表明该内存区是共享的,此时RefCt>1。
Text表明的是文本及代码区,说过几次了,此部分在Hp unix是共享的。
Data表明的是数据区,是一个私有区,如Oracle进程的pga就位于此区。
Stack 即为栈区,这也是一个私有区
MEMMAP 大多表现的是与swap相关的部分
SHMEM 此处是Oracle共享内存

4.4.3 按RSS的定义来算一下
7861真实占用内存(私有区)=

32kb+2.0mb+512kb+….+500kb+0kb+4kb+4kb+8kb+8kb+4kb+384kb=3.6mb


Shared部分均摊=

4kb/137+4kb/55+64.0mb/41+…. +1.1mb/44+1.9mb/41+2.00gb/41=54mb


所以RSS=54+3.6=57.6mb
与57.9mb基本相当,当然这其中有精度及取舍的问题。

5 补充
5.1 如果通过inode发现相应的文件
有的时候进程详细列表显示的不是文件面是inode,如inode:8391,那8391是哪个文件呢?方法如下:

# lsof |grep 8391
oracle 2048 oracle txt REG 64,0x9 77848056 8391 /oracle (/dev/vg00/lv_oracle_software)
oracle 2050 oracle txt REG 64,0x9 77848056 8391 /oracle (/dev/vg00/lv_oracle_software)
oracle 2052 oracle txt REG 64,0x9 77848056 8391 /oracle (/dev/vg00/lv_oracle_software)
oracle 2054 oracle txt REG 64,0x9 77848056 8391 /oracle (/dev/vg00/lv_oracle_software)
oracle 2056 oracle txt REG 64,0x9 77848056 8391 /oracle (/dev/vg00/lv_oracle_software)
# ncheck -i 8391 /dev/vg00/lv_oracle_software
/dev/vg00/lv_oracle_software:
8391 /app/oracle/product/9.2.0/bin/oracle


5.2 如何查看所有进程的实际占用的多少?
可以使用如下命令:

procsize -fcn |sort -rnk 11 | more


每一行,把Total 减掉TEXT项后,再乘上4096大体即为该进程实际占用的大小。

该贴由system转至本版2019-3-2 20:59:34




赞(0)    操作        顶端 
总帖数
1
每页帖数
101/1页1
返回列表
发新帖子
请输入验证码: 点击刷新验证码
您需要登录后才可以回帖 登录 | 注册
技术讨论