【问题标题】:Start JavaFlightRecorder from attached agent or by using com.sun.tools.attach.*;从附加代理或使用 com.sun.tools.attach.* 启动 JavaFlightRecorder;
【发布时间】:2021-02-09 07:38:19
【问题描述】:

是否可以构建自定义代理(或重用现有代理)以在 HotSpot VM 中启用 JFR 功能?

我的计划是构建简单的代理加载器,它使用com.sun.tools.attach.* 包附加到 VM 并加载自定义代理。

我没有故意使用 jcmd 或其他 JDK 工具,因为我无法控制环境,因为应用程序在容器中运行,而我无法控制 jcmd 的 JRE/JDK 和 ABI(所以我无法复制部件JDK 那里只是为了运行命令)。

我知道代理几乎可以做任何事情,因为 jcmd 是用 java 编写的,它能够即时启动 FlightRecording(我假设通过一些 JMX),那么它也应该可以通过 java 代理,但我找不到文档那个。

任何线索都会有所帮助。谢谢

【问题讨论】:

  • 您可以使用jattach - 一个小型的独立非Java实用程序,可以用来代替jcmd来开始飞行记录等。
  • 这是一个复杂的解决方案,因为我必须检测架构并匹配 ABI(如上所述)。最佳方案是基于 Java 的解决方案,因为 Java 类和字节码可以在架构之间传输,并且独立于共享库等。有吗?
  • @apangin 但是你的评论让我找到了潜在的解决方案——它是附加的 API docs.oracle.com/javase/7/docs/jdk/api/attach/spec/index.html,它也应该适用于 Java。感谢您也向我指出 jattach。您能否将其作为答案提供,以便您为此获得荣誉?

标签: java jvm javaagents


【解决方案1】:

Dynamic Attach API (com.sun.tools.attach) 不适用于 JRE 8,因为它需要 tools.jarlibattach.so,它们包含在 JDK 中,但不包含在 JRE 中。

jattach 是一个用 C 语言编写的小型独立实用程序;它为 JRE 提供了动态附加功能,可以用来代替 jcmd:

jattach <pid> jcmd "JFR.start ..."

如果您更喜欢 Java API,您可以使用ByteBuddyAgent。它还提供了不依赖于 com.sun.tools.attach 的动态附加功能。

try (VirtualMachine.ForHotSpot.Connection conn =
             VirtualMachine.ForHotSpot.Connection.ForJnaPosixSocket.Factory
                     .withDefaultTemporaryFolder(30, 100, TimeUnit.MILLISECONDS)
                     .connect(pid)) {
    conn.execute("1", "jcmd", "JFR.start", null, null);
}

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2014-09-08
    • 1970-01-01
    • 1970-01-01
    • 2012-08-07
    • 2016-11-30
    • 1970-01-01
    • 2015-12-16
    相关资源
    最近更新 更多