【发布时间】:2014-06-18 18:35:25
【问题描述】:
我正在尝试衡量在 Windows 7 HotSpot JVM 中使用大内存页面的性能增益。为此,我需要监控 JVM 内存使用情况,以确保实际使用了大页面。不幸的是,我无法实现这一目标。下面是我所做的设置和试验的描述:
环境设置
我正在使用 64 位 Windows 7 终极版进行测试。如Java Support for Large Memory Pages 中所述,启用“锁定内存中的页面”Windows 安全策略。我还验证了通过运行 java version 命令启用了大页面功能,如下所示:
java -XX:+UseLargePages -version
我得到以下结果,表明启用了大页面功能:
java version "1.7.0_60"
Java(TM) SE Runtime Environment (build 1.7.0_60-b19)
Java HotSpot(TM) 64-Bit Server VM (build 24.60-b09, mixed mode)
我在所有试验中都使用了来自 this video 的这个示例 Java 程序来消耗 Java 堆可用的所有内存:
public class InfinteStringHashmap {
public static void main(String[] args) throws Exception{
Map<Long, String> map = new HashMap<Long, String>();
for(long i=1; true; i++){
StringBuilder sb = new StringBuilder();
for(long j=0;j<i;j++) sb.append(" ");
map.put(i, sb.toString());
if(i % 1000 == 0){
System.out.print(".");
Thread.sleep(1000);
}
}
}
}
我使用以下命令运行此示例程序(例如,固定堆大小为 512m):
java -Xms512m -Xmx512m -XX:+UseLargePages InfinteStringHashmap
我还尝试了小至 12MB 和大至 10GB 的其他堆大小。请注意,我在重新启动机器后立即运行我的测试应用程序,以确保我的可用 RAM 内存没有碎片。
内存监控试验失败
为了验证是否使用了Large Memory Pages,我尝试了:
- RamMap tool 来自 Windows SystInternals,它有一个大页面的特定字段。无论我如何更改堆大小,它都不会显示大内存页面的使用情况。为了验证它,我尝试了 MSDN 中的 Creating a File Mapping Using Large Pages 示例来缩小可能性。它工作得非常好(它从代码中打印出 2MB 的页面大小)。 RamMap 工具不显示任何内容。
- 使用this post 中建议的代码打印Java 进程使用的页面大小。它始终打印 4096(Windows 上的默认页面大小)。为了验证它,我按照this video 中的描述在Linux 版本的Hotspot JVM 上尝试了Large Pages,它成功了。但是,打印页面大小不起作用(它一直打印 4096)。
- Vadump 显示有关特定进程的虚拟内存统计信息的工具。 “-o”选项应该显示一个进程使用的VM类型,使用的页面数量,以及每种类型占用的总大小,可以用来推断是否使用了大页面。不幸的是,当我设置 JVM UseLargePages 选项时,此命令失败并显示错误代码 24。
- VmMap 工具不会更新查看的内存列。
- TaskManager 和 Perfmon 等简单监控工具不提供有关大页面的详细信息。
编辑:我尝试了 cmets 中建议的以下工具:
Java Mission Controller:不提供页面大小信息。
进程浏览器:同上
是否可以测量进程的页面大小或监控 Windows 中大内存页面的使用情况?
【问题讨论】:
-
我也对这个感兴趣。 -server -XX:+UseLargePages -XX:+PrintFinalFlags 显示 UseLargePages:=false(为什么?),并且所有堆内存仅在私有工作集中的事实证实了这种情况。为运行 JVM 的用户启用了将页面锁定在内存中的功能,重新启动后最多可释放 12 GB RAM。
标签: java windows memory-management