如何减少Sun/Oracle JVM内部的开销?
如何减少Sun/Oracle JVM内部的开销?
这个问题特别关注在运行于Linux x86-64操作系统上的Sun Java虚拟机(JVM)。我试图找出为什么即使我设置了堆和非堆的限制,Sun JVM也会占用那么多系统物理内存。
我当前运行的是Eclipse 3.7,其中包含多个插件和特性(features)。最常用的特性是PDT、EGit和Mylyn。我使用以下命令行开启Eclipse:
-nosplash -vmargs -Xincgc -Xms64m -Xmx200m -XX:NewSize=8m -XX:PermSize=80m -XX:MaxPermSize=150m -XX:MaxPermHeapExpansion=10m -XX:+UseConcMarkSweepGC -XX:CMSInitiatingOccupancyFraction=70 -XX:+UseCMSInitiatingOccupancyOnly -XX:+UseParNewGC -XX:+CMSIncrementalMode -XX:+CMSIncrementalPacing -XX:CMSIncrementalDutyCycleMin=0 -XX:CMSIncrementalDutyCycle=5 -XX:GCTimeRatio=49 -XX:MaxGCPauseMillis=50 -XX:GCPauseIntervalMillis=1000 -XX:+UseCMSCompactAtFullCollection -XX:+CMSClassUnloadingEnabled -XX:+DoEscapeAnalysis -XX:+UseCompressedOops -XX:+AggressiveOpts -Dorg.eclipse.swt.internal.gtk.disablePrinting
值得注意的是以下这几个开关:
-Xms64m -Xmx200m -XX:NewSize=8m -XX:PermSize=80m -XX:MaxPermSize=150m
这些开关应该将JVM堆的最大限制设置为200 MB,非堆限制设置为150 MB (JConsole标为\" CMS Permanent generation\" 和 \"Code Cache\"). 逻辑上,JVM应该占用350 MB加上JVM所需的内部开销。
实际情况是我的Eclipse进程占用了544.6 MB内存。由ps_mem.py(http://www.pixelbeat.org/scripts/ps_mem.py) 计算可得 ,ps_mem.py计算出了Linux 2.6+内核所保留的物理内存页数。而这是Sun JVM内部开销的35%左右,大约200MB的内存占用!
有什么提示可以缩小这个开销吗?
以下是一些额外的信息:
$ ps auxw USER PID %CPU %MEM VSZ RSS TTY STAT START TIME COMMAND me 23440 2.4 14.4 1394144 558440 ? Sl Oct12 210:41 /usr/bin/java ...
根据JConsole显示,这个进程已经使用了160 MB的堆内存和151 MB的非堆内存。
我并不是说我不能够承载额外的200MB来运行Eclipse,但如果有一种方法可以减少这种浪费,我更愿意用这200MB来做内核块设备缓存或文件缓存。此外,我也有类似的经验,即使用同样的调整可能会减少所有Java程序的开销。
更新:发布问题后,我在SO上找到了之前的帖子:
为什么Sun JVM即使堆,等大小稳定,仍会继续消耗更多的RSS内存?
看起来我应该使用pmap
来解决问题。
admin 更改状态以发布 2023年5月21日