是否有比 jmap 性能更高的堆转储创建替代方案?

是否有比 jmap 性能更高的堆转储创建替代方案?

我必须创建 heapdump,它与 jmap 配合得很好。我的问题是,jmap 创建 heapdump 文件需要很长时间。特别是当堆越来越大(> 1GB)时,它花费的时间太长了。

举个例子:
当服务器的堆空间出现问题时,我想自动重启它并在重启之前创建一个堆转储。这可行,但写入堆转储的时间太长。这样服务器停机时间太长。创建堆转储需要一个多小时。

我知道-XX:+HeapDumpOnOutOfMemoryError,但大多数时候我可以在 jvm 抛出异常之前发现内存问题。

有没有可以代替 jmap 更快地写入堆转储的替代方案?如果能
为上述示例提供特殊解决方案,我们将不胜感激。

这个问题是编程和系统管理的混合,但我认为我在这里处于正确的位置。

答案1

我找到了我的问题的答案。 对 serverfault 上的另一个问题的回答给了我这个想法。

  1. 使用 gdb 连接到你的 java 进程
    gdb --pid=<your java pid>
  2. 从 gdb 创建核心转储
    gcore <file name>
    detach
    quit
  3. 重新启动 Java 进程或做任何你喜欢的事情
  4. 通过将 jmap 连接到核心转储,从核心转储创建堆转储
    jmap -heap:format=b <path to java binary> <core dump file>

在步骤 4 中,指定正确的 java 二进制文件至关重要,否则 jmap 无法附加到核心转储。如果您不确定 java 进程使用了​​哪个二进制文件,请使用 gdb 打开核心转储:
gdb --core=<core dump file>
将会有一行这样的内容,告诉您完整路径:
Core was generated by '/opt/tomcat/bin/jsvc'.

创建核心转储比直接通过 jmap 创建堆转储要快得多。这样,您可以创建 java 进程的堆转储而不会出现太长的停机时间。

编辑:
当您收到以下错误消息时,可能是您指定了错误的 java 二进制文件:

Error attaching to core file: Can't attach to the core file

为了获取 jmap 调用的正确 java 二进制文件,请使用 gdb 打开核心转储:

gdb --core=[path tp core file]

将会有一行这样的内容,告诉你正确的二进制文件:

Core was generated by `/opt/tomcat/bin/jsvc'.

相关内容