【问题标题】:Sun's JVM heap size limit on Ubuntu 64-bitSun 在 64 位 Ubuntu 上的 JVM 堆大小限制
【发布时间】:2011-10-29 01:00:09
【问题描述】:

与 JRockit 相比,我发现在 Sun 的 JVM 上获得的最大堆大小有一些奇怪的行为。

我在 64 位系统 (Ubuntu 11.04) 上的 64 位虚拟机上运行 IDEA。我正在测试的 JVM 版本是:Java HotSpot(TM) 64-Bit Server VM (build 20.1-b02, mixed mode)(我使用apt-get install sun-java6-jdkOracle JRockit(R) (build R28.1.3-11-141760-1.6.0_24-20110301-1432-linux-x86_64, compiled mode)(几个月前我从 Oracle 网站下载的)。

如果我传递参数 -Xms1g -Xmx3g,IDEA 将在 Sun 的 JVM 上报告最大堆大小为 1820M,在 JRockit 上报告为 3072M(如预期)。

如果我通过 -Xms2g -Xmx4g,IDEA 将报告 Sun 的 3640M 和 JRockit 的 4096M。

发生了什么?那些神秘的数字 1820M 和 3640M = 2*1820M 是什么?难道不能以我想要的确切堆大小运行 Sun 的 JVM 吗?

编辑:

一个答案已被删除,所以只是为了让我的 cmets 回来:请注意我说的是 MAX 尺寸,而不是当前尺寸。考虑到我在这里问这个问题之前已经研究了很多,所以没有必要教 Xms、Xmx 或任何其他指定内存区域大小的参数的含义(这些可以在其他地方找到) .

编辑2:

我编写了以下简单代码来测试这种行为:

public static void main(String[] args) throws Exception {
  while (true) {
    final Runtime r = Runtime.getRuntime();
    System.out.println("r.freeMemory() = " + r.freeMemory()/1024.0/1024);
    System.out.println("r.totalMemory() = " + r.totalMemory()/1024.0/1024);
    System.out.println("r.maxMemory() = " + r.maxMemory()/1024.0/1024);
    Thread.sleep(1000);
  }
}

然后我在 Sun 的 JVM 和 JRockit 上使用 -Xmx100m、-Xmx110m、-Xmx120m 等运行了许多不同的值。 Sun 将始终报告 maxMemory() 的奇怪值,并且在运行之间会以大步长(如 30M)增长。 JRockit 每次都会报告准确的值。

【问题讨论】:

  • 顺便说一句,您使用的是什么版本的 JVM?只是想知道。
  • 添加到问题中,因为这可能是我忘记提供的非常相关的信息!

标签: java jvm heap-size


【解决方案1】:

XmsXmx 仅用于指示已分配堆的最小和最大大小。分配的堆的实际大小可能/将是最小值和最大值之间的值,因为 JVM 可以调整堆的大小,尤其是在对象分配事件或垃圾收集事件期间。

如果您需要 JVM 使用“精确”堆大小,您可以指定彼此足够接近的 XmsXmx 值,以便不会发生堆大小调整。当然,这些值必须对应于连续的可用内存量。

以上部分假设了其他内容,出于实际目的可以忽略。

根据用于计算堆大小的代码,应该注意Runtime.maxMemory() returns a value that does not correspond to the value passed in the Xmx flag 用于Hotspot JVM;文档含糊地说它只会返回一个指示 the memory available for the JVM to use 的值。

从您发布的代码的行为推断,堆大小调整将导致针对Runtime.maxMemory() 的不同调用报告不同的值。此外,无需指出 JRockit JVM 报告通过 Xmx 标志传入的值。

【讨论】:

  • 也许你误读了我的问题,或者我没有正确表达自己。我不是在谈论堆的使用不是指定的确切值。我是说 JVM 报告的最大可用堆不是我指定的值,就 Sun 的 JVM 而言。这是 JRockit 上的正确值。显然,实际的堆使用量会随时间变化,并且会在 Xms 和 Xmx 之间。我在说的是 Sun 没有识别出 Xmx 的正确值,而是使用了 1820 的倍数。
  • 如何获得最大堆大小?我想 IDEA 报告的是当前而不是最大堆大小。
  • 不,维内特。 IDEA 报告当前和最大堆大小。我说的是最大堆大小。电流对我来说看起来是正确的(不断增长,增长,然后在垃圾收集上缩小)。考虑到我在这里问这个问题之前已经做了很多研究。
  • 这是否意味着Sun实际上忽略了Xmx参数?
  • 不,这意味着您不应该使用 Runtime.maxMemory 来读取 Xmx 的值。对于 HotSpot 来说,它们是两种不同的东西。
猜你喜欢
  • 2014-03-14
  • 2017-06-05
  • 2011-01-28
  • 2013-02-12
  • 2012-06-08
  • 2012-04-30
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多